题目来源:
PTA | 程序设计类实验辅助教学平台
题目内容:
给定 N 个非 0 的个位数字,用其中任意 2 个数字都可以组合成 1 个 2 位的数字。要求所有可能组合出来的 2 位数字的和。例如给定 2、5、8,则可以组合出:25、28、52、58、82、85,它们的和为330。
输入格式:
输入在一行中先给出 N(1 < N < 10),随后给出 N 个不同的非 0 个位数字。数字间以空格分隔。
输出格式:
输出所有可能组合出来的2位数字的和。
输入样例:
3 2 8 5
输出样例:
330
代码实现(代码一):
我的暴力解法。时间复杂度:O(n*n)
#include <iostream>using namespace std;int main(){int n;cin>>n;int a[n];for(int i=0;i<n;i++) cin>>a[i];int num=0;for(int i=0;i<n;i++){for(int j=0;j<n;j++){if(i!=j){num=num+a[i]*10+a[j];}} }cout<<num; return 0;}
代码实现(代码二):
参考大佬的解法。时间复杂度:O(n)
#include <cstdio>
int main() {int N, sum = 0, temp;scanf("%d", &N);for (int i = 0; i < N; i++) {scanf("%d", &temp);//每个数字都能在个位出现(N-1)次,十位出现(N-1)次sum += temp * 10 * (N - 1) + temp * (N - 1);}printf("%d", sum);return 0;
}
题目心得:
1.这题的最优解法,真的很难想到,它不是区别在你要用什么“固定的套路”去解决问题。
而是抽象为一个数学问题,逆向思维,//每个数字都能在个位出现(N-1)次,十位出现(N-1)次
2.换个角度想,以后你也可以抛弃算法的视角,从数学问题的交付出发解决问题。