最大数和位置(无数组)
#include<iostream>
using namespace std;
int main() {
int a, max = 0, num;
for (int i = 1; i <= 100; i++) {
cin >> a;
if (a > max) { max = a; num = i; }
}
cout << max << endl << num;
return 0;
}
递增序列 while(cin>>n,n)
#include<iostream>
using namespace std;
int main() {
int a;
//或者是(cin>>a&&a)
while (cin >> a, a) {
for (int i = 1; i <= a; i++)cout << i << " ";
cout << endl;
}
}
斐波那契数列前n项
#include<iostream>
using namespace std;
int main() {
int n,a=0,b=1,c;
cin>>n;
for (int i = 0; i < n; i++) {
cout << a <<" ";
c = a + b;//求下一项
//更新前两项
a = b;
b = c;
}
return 0;
}
因子暴力超时优化思路 :开平方思想
原理:因为如果j
是x
的一个因子,那么x/j
也必然是x
的一个因子,且j
和x/j
中至少有一个不会超过sqrt(x)
。
完全数优化
超时分析:(还没学时空复杂度)暴力查找因子时需要遍历1到数x,如果x特别大的话内层就需要循环很多次和外层相乘后次数就更多了,所以很容易超时。
#include<iostream>
#include <cmath>
using namespace std;
int main() {
int n,x,sum=0;
cin >> n;
for (int i = 1; i <= n; i++) {
cin >> x;
if(x==1)cout<< x << " is not perfect" << endl;
else {
sum++;
for (int j = 2; j <= sqrt(x); j++) {
if (x % j == 0) {
int y = x / j;
if (y == j) sum = sum + j;
else sum = sum + j + y;
}
}
if (sum == x) cout << x << " is perfect" << endl;
else cout << x << " is not perfect" << endl;
}
sum = 0;
}
return 0;
}
素数优化
原理同上
#include<iostream>
#include<cmath>
using namespace std;
int main() {
int n;
cin >> n;
for (int i = 1; i <= n; i++) {
int x = 0;
bool is_prime = 1;
cin >> x;
if (x < 2) {
cout<< x << " is not prime" << endl;
continue;
}
//因子成对出现且有一个不会大于x开平方
for (int j = 2; j <= sqrt(x); j++) {
if (x % j == 0) {
is_prime = 0;
break;
}
}
if(is_prime==1)cout << x << " is prime" << endl;
else cout << x << " is not prime" << endl;
}
return 0;
}
哈曼顿距离 -- 打印菱形
哈曼顿距离:点和中心的横纵坐标的差的绝对值之和。
打印菱形所满足的点就是两点距离小于等于这个距离的点,而对应的哈曼顿距离就是n/2(小数部分被省略,等价于(n-1)/2)。
#include<iostream>
using namespace std;
int main() {
int n;
cin >> n;
for (int i = 0; i < n; i++) {
for (int j = 0; j < n; j++) {
if (abs(i - n / 2) + abs(j - n / 2)<=n/2)cout << "*";
else cout << " ";
}
cout << endl;
}
return 0;
}
二选一,三目运算符的使用(AcWing743)
#include<iostream>
using namespace std;
int main() {
double n, x, sum = 0;
char a;
cin >> n >> a;
for (int i = 0; i < 12; i++) {
for (int j = 0; j < 12; j++) {
cin >> x;
if (i == n) sum += x;
}
}
printf("%.1lf", a == 'S' ? sum : sum / 12);
return 0;
}
二维数组求右上角之和或平均数(哈曼顿+三目)AcWing745
#include<iostream>
#include<cmath>
using namespace std;
int main() {
double x, sum = 0;
char a;
cin >> a;
for (int i = 0; i < 12; i++) {
for (int j = 0; j < 12; j++) {
cin >> x;
if (i+11-j<=10) {//i<j更简单,但如果改成左上角就用哈曼顿(i+j<=10)
sum += x;
}
}
}
printf("%.1lf", a == 'S' ? sum : sum / 66);
return 0;
}
如果换成左上方,用曼哈顿就比较复杂,奇数还好,偶数需要两个中心。如下:
#include<iostream>
#include<cmath>
using namespace std;
int main() {
double x, sum = 0;
int count = 0;
char a;
cin >> a;
for (int i = 0; i < 12; i++) {
for (int j = 0; j < 12; j++) {
cin >> x;
if (i <= 4 && j <= 5) {
if (i + 5 - j <= 4) {//容易错
sum += x;
count++;
}
}
if (i <= 4 && j >= 6) {
if (i + j - 6 <= 4) {//容易错
sum += x;
count++;
}
}
}
}
printf("%.1lf", a == 'S' ? sum : sum / count);
return 0;
}
所以用i和j的表达式判断会比较简单
#include<iostream>
#include<cmath>
using namespace std;
int main() {
double x, sum = 0;
int count = 0;
char a;
cin >> a;
for (int i = 0; i < 12; i++) {
for (int j = 0; j < 12; j++) {
cin >> x;
if (j > i && i + j < 11) {//上方
sum += x;
count++;
}
}
}
printf("%.1lf", a == 'S' ? sum : sum / count);
return 0;
}
小总结:二维数组的各个区
以12x12的数组为例:
四个半区:
右上:j > i
右下:i + j > 11
左上:i + j < 11
左下:i > j
四个四分之一区:(取交集)
上:j > i && i + j < 11
下:i > j && i + j > 11
左:i > j && i + j < 11
右:j > i && i + j > 11