1.用筛法求100之内的素数。
筛法又称为筛选法,具体做法是:先把N个自然数按次序排列起来。1不是质数,也不是合数,要划去。第二个数2是质数留下来,而把2后面所有能被2整除的数都划去。2后面第一个没划去的数是3,把3留下,再把3后面所有能被3整除的数都划去。3后面第一个没划去的数是5,把5留下,再把5后面所有能被5整除的数都划去。这样一直做下去,就会把不超过N的全部合数都筛掉,留下的就是不超过N的全部质数。因为希腊人是把数写在涂腊的板上,每要划去一个数,就在上面记以小点,寻求质数的工作完毕后,这许多小点就像一个筛子,所以就把埃拉托斯特尼的方法叫做“埃拉托斯特尼筛”,简称“筛法”。
详细解释见:https://baike.baidu.com/item/%E7%AD%9B%E9%80%89%E6%B3%95/9393288?fr=aladdin
//筛法求素数
#include <iostream>
#include <cmath>
using namespace std;
int main()
{
int i,j,a[100];
for (i=0; i<100; i++)
a[i] = i+1;
for (i = 1; i < sqrt(100); i++)
for (j = i+1; j < 100; j++)
{
if (a[i]!=1 && a[j]!=1)
if(a[j]%a[i]==0)
a[j]=1;
}
for (i = 0; i<100;i++)
{
if(a[i]!=1)
cout <<a[i]<<'\t';
}
}
这里运用了一个简便算法是,把除数a[i]限定在1到sqrt(100)的范围内,也就是后边的除数其实也是这些数的倍数,因此这样减少运算时间。
2. 用选择法对10个整数排序
简单选择排序的基本思想:第1趟,在待排序记录r[1]~r[n]中选出最小的记录,将它与r[1]交换;第2趟,在待排序记录r[2]~r[n]中选出最小的记录,将它与r[2]交换;以此类推,第i趟在待排序记录r[i]~r[n]中选出最小的记录,将它与r[i]交换,使有序序列不断增长直到全部排序完毕。
详见:https://baike.baidu.com/item/%E9%80%89%E6%8B%A9%E6%8E%92%E5%BA%8F%E6%B3%95/2304587?fr=aladdin
//用选择法对是个整数排序(由小到大)
#include <iostream>
using namespace std;
int main()
{
int i,j,a[10];
int k,temp;
//输入
for (i=0; i<10; i++)
cin >> a[i];
//排序
for (i=0;i<9;i++)
{
k = i;
for(j=i+1;j<10;j++)
if(a[j]<a[k]) k=j;//k下标用来储存当前最小值
temp = a[k];
a[k] = a[i];
a[i] = temp;
}
//输出
for (i=0;i<10;i++)
cout << a[i] <<' ';
}
由于要找整个数组的最小值与最前边的元素交换,因此需要随时储存并更新当前的最小值,因此需要引入一个记录当前最小值位置的索引k。
3. 求一个3 x 3整型矩阵主对角线元素之和
此处注意:不能试图通过输入大小来定义数组,数组的大小在定义时必须是确定的
即:
const int n = 5;
int a[n];
是对的,n为不可变的5,数组维度为5
而:
int n;
cin >> n;
int a[n];
是错误的
#include <iostream>
using namespace std;
int main()
{
int i,j,a[3][3];
for (i = 0; i < 3; i++)
for (j = 0; j < 3; j++)
cin >> a[i][j];
int s = 0;
for (i = 0; i < 3; i++)
s = s + a[i][i];
cout << s;
}
4. 有一个已排好序的数组,要求输入一个数后,按原来排序的规律将它插入数组中。
思路:假设原数组由小到大排列的,则当发现插入的数字大于原数组的某个元素时,将原数组从最后一个元素开始,到这个元素为止,依次向后挪一个位置,再将插入的元素放入这个元素的位置即可。
//有一个已排好序的数组,要求输入一个数后,按原来排序的规律将它插入数组中。
#include <iostream>
using namespace std;
int main()
{
int a[11] = {1,4,5,6,9,10,22,34,67,79};
int num,i,j;
cin >> num;
if (num > a[9])
a[10]=num;
else
{for (i=0;i<10;i++)
{if (a[i]>num)
{for (j=9;j>=i;j--)
a[j+1]=a[j];//依次往后挪一个
a[i]=num;
break;
}
}
}
for (i=0;i<11;i++)
cout<<a[i]<<" ";
}
5. 将一个数组中的值按逆序重新存放。例如,原来顺序为8,6,5,4,1。要求改为1,4,5,6,8
思路:对称位置对换即可
//将一个数组中的值按逆序重新存放。例如,原来顺序为8,6,5,4,1。要求改为1,4,5,6,8
#include <iostream>
using namespace std;
int main()
{
const int n = 4;
int i,t,a[n];
for(i = 0;i<n;i++)
cin >> a[i];
for(i=0;i<n/2;i++)
{
t = a[i];
a[i] = a[n-i-1];
a[n-i-1] = t;
}
for(i=0;i<n;i++)
cout << a[i] <<' ';
}
6. 打印杨辉三角,10行即可
思路:先把边上的1打出来,然后中间数是其上边和左上角数的加和
//打印杨辉三角
#include <iostream>
using namespace std;
int main()
{
const int n =10;
int i,j,a[n][n];
for (i=0;i<n;i++)
{
a[i][i]=1;
a[i][0]=1;
}
for (i=2;i<n;i++)
{
for(j=1;j<=i-1;j++)
a[i][j]=a[i-1][j-1]+a[i-1][j];
}
for (i = 0; i<10;i++)
{
for(j=0;j<=i;j++)
cout << a[i][j] <<' ';
cout << '\n';
}
}
7.找出一个二维数组的“鞍点”,即该位置上的元素在该行上最大,在该列上最小。也可能没有鞍点。
思路:大循环找行上的最大值,然后标记该最大值及其列的位置,然后小循环判断该列有没有比最大值小的点,有则不是鞍点,继续寻找,没有则是鞍点,获得鞍点可直接跳出,则直接结束大循环。
//找出二维数组的鞍点
#include <iostream>
using namespace std;
int main()
{
const int n=4,m=5;
int i,j,a[n][m];
bool flag = true;
//输入
for (i = 0; i < n; i++)
for(j = 0; j <m; j++)
cin >> a[i][j];
//找行最大值所在的位置
int max,maxj;
for (i=0;i<n;i++)
{
max=a[i][0];
maxj=0;
for (j=0;j<m;j++) //找出第i行中的最大数
if (a[i][j]>max)
{
max=a[i][j]; //将本行的最大数存放在max中
maxj=j; //将最大数所在的列号存放在maxj中
}
//判断行上的最大值是不是列上的最小值
int k;
for (k = 0; k< n; k++)
{
if (max > a[k][maxj])
{
flag = false;
continue;
}
}
if(flag) //如果flag1为真表示是鞍点
{
cout<<"a["<<i<<"]"<<"["<<maxj<<"]="<<max<<endl;
//输出鞍点的值和所在行列号
break; //只找出一个鞍点即可
}
}
if(!flag) //如果flag为假表示鞍点不存在
cout<<"It does not exist!"<<endl;
}
8. 有15个数按由大到小顺序存放在一个数组中,输入一个数,要求用折半查找法找出该数是数组中第几个元素的值。如果该数不在数组中,则输出“无此数”。
//折半法找数
#include <iostream>
using namespace std;
int main()
{
const int n=15;
int i, a[n] = {1,2,4,5,6,9,10,15,18,20,21,26,30,40,60};
int left=0,right=n-1,mid;
int num;
cin >> num;
if(num>a[right] || num < a[left])
{
cout << "无此数";
}
while(left <= right)
{
mid = (left + right)/2;
if (num == a[mid])
{
cout <<"该数所在位置为" << mid+1;
break;
}
else if(num <a[mid]) //左边
{
right = mid - 1;
}
else if(num >a[mid])
{
left = mid + 1;
}
}
if(num != a[mid])
cout << "无此数";
}
9. 给出年、月、日,计算该日在该年中是第几天。
思路:把月份的天数做成数组,按月把前边的天数相加,闰年加一天即可。
//给出年月日计算是一年的第几天
#include <iostream>
using namespace std;
int main()
{
int year,month,day,sumday=0;
int days_sum(int month, int day);
int leap(int year);
//输入
cin >> year >> month >> day;
//计算天数
sumday = days_sum(month,day);
//判断闰年
if(leap(year) && month >= 3)
sumday = sumday + 1;
cout <<"该日期是一年的第:"<<sumday<<" 天";
return 0;
}
int days_sum(int month,int day) //计算日期
{int i;
int day_tab[12]={31,28,31,30,31,30,31,31,30,31,30,31};
for (i=0;i<month-1;i++)
day+=day_tab[i];
return(day);
}
int leap(int year) //判断是否为闰年
{int leap;
leap=year%4==0&&year%100!=0||year%400==0;
return(leap);
}
10.有一篇文章,共有3行文字,每行有个80字符.要求分别统计出其中英文大写字母、小写字母、空格以及其它字符的个数。
//统计大小写字母数
#include <iostream>
using namespace std;
int main()
{
int i,j,upper,lower,digit,space,other;
char text[3][80];
upper=lower=digit=space=other=0;
for (i=0;i<3;i++)
{cout<<"please input line "<<i+1<<endl;
gets(text[i]);
for (j=0;j<80 && text[i][j]!='\0';j++)
{if (text[i][j]>='A'&& text[i][j]<='Z')
upper++;
else if (text[i][j]>='a' && text[i][j]<='z')
lower++;
else if (text[i][j]>='0' && text[i][j]<='9')
digit++;
else if (text[i][j]==' ')
space++;
else
other++;
}
}
cout<<"upper case:"<<upper<<endl;
cout<<"lower case:"<<lower<<endl;
cout<<"digit :"<<digit<<endl;
cout<<"space :"<<space<<endl;
cout<<"other :"<<other<<endl;
return 0;
}
11.打印以下图案
(1)用字符数组法的代码如下:
//用字符串数组打印平行四边形
#include <iostream>
using namespace std;
int main()
{
char c[5] = {'*','*','*','*','*'};
int i,j,k;
for (i = 0; i < 5; i++)
{
for (j = 1; j<=i; j++)
cout <<' ';
for (k = 0; k < 5;k++)
cout << c[k];
cout <<'\n';
}
}
(2)用string方法的代码如下:
要注意的是,string作为头文件要写出,否则报错。
//用string法打印平行四边形
#include <iostream>
#include <string>
using namespace std;
int main()
{
string str = "*****";
int i,j;
for (i = 0; i<5;i++)
{
for(j = 1; j<=i; j++)
cout << ' ';
cout << str << endl;
}
}
12. 有一行电文,已按下面规律译成密码:
A->Z a->z
B->Y b->y
C->X c->x
… …
即第一个字母变成第26个字母,第i个字母变成第(26-i+1)个字母。非字母字符不变,要求编程序将密码译回原文,并打印出密码和原文。
//电文译码
#include <iostream>
using namespace std;
int main()
{
int j,n;
char ch[80];
cout<<"input cipher code:";
gets(ch);
j=0;
while (ch[j]!='\0')
{
if ((ch[j]>='A') && (ch[j]<='Z'))
ch[j]=155-ch[j];
else if ((ch[j]>='a') && (ch[j]<='z'))
ch[j]=219-ch[j];
else
ch[j]=ch[j];
j++;
}
n=j;
cout<<"original text:";
for (j=0;j<n;j++)
putchar(ch[j]);
cout<<endl;
return 0;
}
注意:这里的转换相当于原文和密文字母顺序之和永远为26,也就是ACSII码和值固定,若是大写字母,则二者之和为65(A)+90(Z)=150;而小写字母为97(a)+122(z)=219,因此用和值减去密文则得到原文。
13.编写一个程序,将两个字符串连接起来,结果取代第一个字符串。
(1) 用字符数组,不用strcat函数(即自己写一个具有strcat函数功能的函数);
//字符数组连接两个字符
#include <iostream>
using namespace std;
int main()
{
char str1[80],str2[40];
int i=0,j=0;
cout<<"input string1:";
cin >> str1;
cout<<"input string2:";
cin >> str2;
while(str1[i]!='\0')
i++;
while(str2[i]!='\0')
str1[i++] = str2[j++];
str1[i] = '\0';
cout << "The new string is:"<<str1;
}
(2) 用标准库中的strcat函数;
//用strcat函数连接字符串
#include <iostream>
using namespace std;
int main()
{
char str1[80],str2[40];
cout<<"input string1:";
cin >> str1;
cout<<"input string2:";
cin >> str2;
cout << strcat(str1,str2);
}
(3) 用string 方法定义字符串变量。
//用sring连接字符串
#include <iostream>
#include <string>
using namespace std;
int main()
{
string str1,str2,s;
cout<<"input string1:";
cin >> str1;
cout<<"input string2:";
cin >> str2;
s = str1 + str2;
cout <<s;
}
注意:用string连接两个字符串可以直接相加。
14.输出n个字符串,把它们按照字母由小到大的顺序排列并输出。
思路:冒泡法
//n个字符串排序
#include <iostream>
#include <string>
using namespace std;
int main()
{
const int n = 5;
int i,j;
string str[n],temp;
for (i = 0; i<n;i++)
cin >> str[i];
for (i = 0; i < n-1; i++)//冒泡
for(j = 0; j < n-i-1;j++)
if(str[j]>str[j+1])
{
temp=str[j];
str[j]=str[j+1];
str[j+1]=temp;
}
cout<<endl<<"sorted strings:"<<endl;
for(i=0;i<n;i++)
cout<<str[i]<<endl;
return 0;
}
15. 输入n个字符串,把其中以字母A打头的字符串输出。
//把字符串中A打头的字符串输出
#include <iostream>
#include <string>
using namespace std;
int main()
{
const int n = 5;
string str;
int i;
for (i = 0; i < n; i++)
{
cin >> str;
if(str[0] == 'A')
cout << str;
}
}
16. 输入一个字符串,把其中的字符按逆序输出。如输入LIGHT,输出THGIL.
(1) 用字符数组方法;
//用字符数组逆序输出字符串
#include <iostream>
using namespace std;
int main()
{
const int n = 5;
char str[n],temp;
int i;
for (i = 0;i<n;i++)
cin >> str[i];
for(i = 0;i<n/2;i++)
{
temp = str[i];
str[i] = str[n-i-1];
str[n-i-1] = temp;
}
for(i = 0;i<n;i++)
cout << str[i];
}
(2)用string 方法
//string方法逆转字符串
#include <iostream>
#include <string>
using namespace std;
int main()
{
string a;
int i,n;
char temp;
cout<<"please input a string:";
cin>>a;
n=a.size();
for(i=0;i<n/2;i++)
{
temp=a[i];
a[i]=a[n-i-1];
a[n-i-1]=temp;
}
cout<<a<<endl;
return 0;
}
注意:string方法有函数.size可以直接求出字符串长度
17.输入10个学生的姓名,学号和成绩,将其中不及格的姓名、学号和成绩输出。
//输出不及格学生的姓名、学号、成绩
#include <iostream>
#include <string>
using namespace std;
const int n = 10;
string name[n];
int num[n],score[n];
int main()
{
int i;
void input_data();
input_data();
cout<<endl<<"The list of failed:"<<endl;
for(i=0;i<n;i++)
if(score[i]<60)
cout<<name[i]<<" "<<num[i]<<" "<<score[i]<<endl;
return 0;
}
void input_data()
{
int i;
for (i=0;i<n;i++)
{
cout<<"input name,number and score of student "<<i+1<<":";
cin>>name[i]>>num[i]>>score[i];
}
}