CF952F 2 + 2 != 4 題解
超級毒瘤愚人節玄學題???
luogu傳送門
題意簡述
按照樣例的方式計算題目給出的表示式的值???
\(\texttt{SOLUTION}\)
首先我們來看一下樣例:
- 樣例一:\(8-7+6-5+4-3+2-1-0=0=0(\text{正常運算中表達式的值})+0\)
- 樣例二:\(2+2=-46=4(\text{正常運算中表達式的值})-5\times 10^1\)
- 樣例三:\(112-37=375=70(\text{正常運算中表達式的值})+3\times 10^2\)
看到這我們發現 \(0,50,300\) 這些數都很有規律,於是開始思考:他們是怎麼來的呢?
首先看樣例一的式子,它的值為 \(4\)
發現只有樣例一中的 \(+\) 號和 \(-\) 號個數相同。
於是我們下意識的從符號下功夫。
作為一個合格的 \(\text{OIer}\) 你一定對字元的 \(\texttt{ASCII}\) 十分熟悉吧。
我們翻了翻 \(\texttt{ASCII}\) 編碼表(大霧)發現 \(-\) 的 \(\texttt{ASCII}\) 編碼為 \(45\) ,個位數為 \(5\), \(+\) 的 \(\texttt{ASCII}\) 編碼為 \(43\) ,個位數為 \(3\)。
然而,樣例二卻是 \(-\) \(\color{red}5\) \(\times 10^1\)
又發現
- \(10^1\) 中的 \(1\) 就是 \(2\) (\(+\) 號後數字)的位數。
- \(10^2\) 中的 \(2\) 就是 \(37\) (\(-\) 號後數字)的位數。
於是我們就猜出了結論:按照正確計算方法計算完畢原式的值後,對於每個符號 \(+\), 減去 \(3\times 10^{+ \text{後數字的位數}}\)。對於每個符號 \(-\)
快速的打完了程式碼。
A?
A了。
真是不可思議!!!
至於為什麼 \(+\) 是減去 “ \(3\) ” 而 \(-\) 是加上 “ \(5\) ”,參考了其他題解,原來並不是因為把 \(\texttt{ASCII}\) 的個位數反過來,而是把符號也當做數字來看,\(0\) 的 \(\texttt{ASCII}\) 為 \(48\) 而 \(|43-48|=5\),\(|45-48|=3\) ,所以 \(+\) 是減去 “ \(3\) ” 而 \(-\) 是加上 “ \(5\) ”。
\(\texttt{AC CODE}\)
#include<bits/stdc++.h>
#define IN inline
const int N=100010;
int n,ans;
char str[N];
int main()
{
scanf("%s",str+1);
n=strlen(str+1);
int i=1;
while(str[i]>='0'&&str[i]<='9'&&i<=n)//第一個數沒有符號,特判
{
ans=ans*10+str[i]-'0';//儲存每個符號之後的數字的值
++i;
}
while(i<=n)
{
if(str[i]=='+')
{
int ws=0,num=0;
++i;
while(str[i]>='0'&&str[i]<='9'&&i<=n)
{
++ws;//儲存每個符號之後的數字位數
num=num*10+str[i]-'0';//儲存每個符號之後的數字的值
++i;
}
ans=ans-5*std::pow(10,ws)+num;
}
else if(str[i]=='-')
{
int ws=0,num=0;
++i;
while(str[i]>='0'&&str[i]<='9'&&i<=n)
{
++ws;//儲存每個符號之後的數字位數
num=num*10+str[i]-'0';//儲存每個符號之後的數字的值
++i;
}
ans=ans+3*std::pow(10,ws)-num;
}
}
printf("%d",ans);
return 0;
}
\(\text{P.S}\). 這題難度嚴重惡評,這思維難度至少紫題吧!!!