题解:简单思维题,从第二个开始,选择与前一个绝对值最小的就行。
#include<bits/stdc++.h>
using namespace std;
#define sc(x) scanf("%d",&x)
#define sl(x) scanf("%lld",&x)
#define ll long long
#define pb push_back
typedef pair<int,int>PII;
const int Max=1e6+5;
const ll INF=1e15+5;
const ll mod=1e9+7;
ll a[100];
ll b[100];
int n;
int main(){
int t;sc(t);
while(t--){
sc(n);
ll sum=0;
for(int i=0;i<n;i++) sl(a[i]);
for(int i=0;i<n;i++) sl(b[i]);
for(int i=1;i<n;i++){
sum+=min(abs(a[i]-a[i-1])+abs(b[i]-b[i-1]),abs(a[i]-b[i-1])+abs(b[i]-a[i-1]));
}
printf("%lld\n",sum);
}
}
题解:很容易知道2^15=32768,故不管什么数经过v=(2⋅v)mod32768的15次变换都会等到0的结果,所以只需要先进行操作一ai--ai+15,然后循环第二个操作得到0的结果,最后取最小值就行。
#include <bits/stdc++.h>
using namespace std;
int n, mod = 32768;
int cal(int x){
int ans = 20;
for (int i = 0; i <= 15; i ++ ){
int t = (x + i) % mod, cnt = i;
while ( t != 0 ){
t = t * 2;
t %= mod;
cnt++;
}
ans = min(ans, cnt);
}
return ans;
}
int main(){
cin >> n;
vector <int> a(n);
for (int i = 0; i < n; i ++ )
cin >> a[i];
for (int i = 0; i < n; i ++ )
cout << cal(a[i]) << " \n"[i == n - 1];
return 0;
}
题解:很明显 所有的数都至少要加到maxa(数组最大值),但是不一定是加到maxa是最节省的。最多maxa+3,因为3已经是一个循环(1 2)。
例如:
5
3 3 3 3 4
如果都加到4,就是 1 2 1 2 1 2 1 花七天
如果是5 就是 1(给4即可) 2 1 2 1 2 花六天
线性做法,就是先消耗不得不取1的数目,然后剩下的奇数天来填2,让使用天数尽可能多。
#include<bits/stdc++.h>
using namespace std;
#define sc(x) scanf("%d",&x)
#define sl(x) scanf("%lld",&x)
#define ll long long
#define pb push_back
typedef pair<int,int>PII;
const int Max=1e6+5;
const ll INF=1e18+5;
const ll mod=32768;
ll a[Max];
int main(){
// int u=(1e9/2-1)*3;
// cout<<u<<endl;
int t;sc(t);
while(t--){
int n;sc(n);
ll ans=0;ll maxa=0;
ll mina=INF;
for(int i=0;i<n;i++) sl(a[i]),maxa=max(maxa,a[i]);
for(ll j=0;j<=2;j++){
maxa+=j;
ll num1=0,num2=0;
for(int i=0;i<n;i++){
ll k=maxa-a[i];
num2+=k/2;
if(k%2==1) num1++;
}
if(num1>num2) mina=min(mina,num1*2-1);
else if(num1==num2) mina=min(mina,num1*2);
else{
ll sum=num1*2;num2-=num1;
if(num2==1) sum+=2;
else{
sum+=num2/3*4;
num2%=3;
if(num2==1) sum+=2;
else if(num2==2) sum+=3;
}
mina=min(mina,sum);
}
}
printf("%lld\n",mina);
}
}