第二次上机作业(2020.12.5)

题目一
已知一个矩阵,存储在一个二维数组中。将矩阵中和值为最大的那一行
元素与首行对换。

思路:先定义short类型smax并取最小值,对矩阵中每一行求和,将第一行的和值赋给smax,再对后面每一行求和,比较得出最大值,并得出最大值的行数row。最后利用for循环将和值最大的一行的每个元素与第一行互换。
代码如下

#include<iostream>
using namespace std;
int main() {
	short arr[5][5], s, smax = -32768, row,t;
	for (int i = 0; i <= 4; i++) {
		s = 0;
		for (int j = 0; j <= 4; j++) {
			s += arr[i][j];
		}
		if (s > smax) {
			smax = s; 
			row = i;
		}
	}
	for (int j = 0; j <= 4; j++) {
		t = arr[0][j];
		arr[0][j] = arr[row][j];
		arr[row][j] = t;
	}
    system("pause");
	return 0;
}

题目二
已知一个方阵,存储在一个二维数组中。用指针访问数组元素的方法,计算方阵中上三角所有元素的和、下三角所有元素的和,以及主对角线上的所有
元素和。
思路:先定义方阵arr,再定义指向其的指针p,并用p来访问数组中的元素,通过循环一次求出所需值。
代码如下

#include<iostream>
using namespace std;
int main() {
	int arr[5][5] = { {1},{3},{5},{7},{9} };
	int(*p)[5] = arr;
	int i, j, sum1=0, sum2=0, sum3=0;
	for (int i = 0; i <= 4; i++) {
		for (int j = 4; j >= i; j--) {
			sum1 += p[i][j];
		}
	}
	cout << sum1 << endl;
	for (int i = 0; i <= 4; i++) {
		for (int j = 0; j <=i; j++) {
			sum2 += p[i][j];
		}
	}
	cout << sum2 << endl;
	for (int i = 0; i <= 4; i++) {
		for (int j = 0; j == i; j++) {
			sum3 += p[i][j];
		}
	}
	cout << sum3 << endl;
	system("pause");
	return 0;
}

题目三
判断字符串是否是“回文”。所谓“回文”是指顺读和逆读都是一样的串,例如串 12321 和 madam 都是回文。

#include <iostream>
using namespace std;
const int SZ = 100;
int main()
{
char carray[SZ];
int is_palindrome = 1;
cout << "Please input a string .." << endl;
cin.get(carray, SZ);
int len = strlen(carray);
for (int i = 0; i < len/2; i++)
{
if (carray[i] != carray[len - 1 - i])
{
is_palindrome = 0;
break;
}
}
if (is_palindrome)
cout << "The string is a palindrome" << endl;
else
cout << "The string is not a palindrome" << endl;
return 0;
}

要求:重新定义回文为:虑去所有非字母字符(包括空格)后,不考虑字母的大小写,从左向右和从右向左读都相同的词或短语。如“Madam,I’m adam”和“Golf,No Sir,prefer prison flog!”。改写上面程序,用string来代替字符数组来完成相同操作。

思路:本题主要通过carray1中的每个字符的ASCII码来判断字符是否为非小写字母字符,并将数字和符号删去,将大写字母通过ASCII码加32转化为小写。将满足条件的carray1中的字符通过加法运算赋值给空字符串carray2,由此来判断carray1是否为新定义的回文数。
代码如下

#include <iostream>
#include<string>
using namespace std;
int main(){
	string carray1, carray2;
	int is_palindrome = 1;
	cout << "Please input a string :" << endl;
	getline(cin, carray1);
	int len1 = carray1.length();
	for (int i = 0; i < len1; i++) {
		if (carray1[i] > 64 && carray1[i] < 123) {
			if (carray1[i] > 64 && carray1[i] < 91) {
				carray1[i] += 32; 
				carray2 += carray1[i];	
				continue;
			}
			if (carray1[i] > 96 && carray1[i] < 123) { 
				carray2 += carray1[i]; 
			}
		}
	}
	int len2 = carray2.length();
	for (int i = 0; i < len2 / 2; i++)
	{
		if (carray2[i] != carray2[len2 - 1 - i])
		{
			is_palindrome = 0;
			break;
		}
	}
	if (is_palindrome)
		cout << "The string is a palindrome" << endl;
	else
		cout << "The string is not a palindrome" << endl;
	return 0;
}

题目四
约瑟夫问题:n 个人围成一圈,从 1 开始顺序编号;游戏开始,首先生成一个 1-n 区间内的随机数,从第一个人开始由 1 到 m 循环报数,报到 m 的人退出圈外,问最后留下的那个人原来的序号。
提示:本题可以定义一个容器(vector),初始化大小(元素个数)为 n。容器里元素的值用来标识该人是否出局,1 在圈内,0 出局。值为 0 的元素不参加报数。此外,vector 容器中的元素是线性排列的,而人是围成圈的,用容器表示要有一种从容器尾部跳到其头的技巧,即下标加 1 除以 n 求余数。

思路:生成伪随机数n,并通过运算得到介于1到n之间的一个数m,定义一个含有n个1的bool类型容器v,对容器中的每个元素进行访问,如果元素是1,则进行报数(num1+1),当num1等于m时,将本次访问的元素赋值为0,不参与报数。当循环到容器尾部时,令其继续循环,直到容器内值为1的元素个数num2=1,退出循环,最后利用循环依次访问处理后的容器中的元素,输出值为1的元素的序号。
代码如下

#include<iostream>
#include<vector>
using namespace std;
int main() {
	int n = rand();
	int m = rand() % n + 1;
	int num1 = 0, num2 = n;
	cout << n << " " << m << endl;
	vector<bool>v ;
	for (int i = 0; i < n; i++) {
		v.push_back(1);
	}
	for (int j = 0; j < n; j++) {
		if (v.at(j) == 1) {
			num1++;
			if (num1 == m) {
				v.at(j) = 0;
				num1 = 0;
				num2--;
				if (num2 == 1)break;
			}
		}
		if (j == n - 1 && num2 != 1) {
		j = -1;
		continue;
	    }
	}
	for (int i = 0; i < n; i++) {
		if (v.at(i) == 1) {
			cout << i + 1 << endl;
		}
	}
	system("pause");
	return 0;
}

总结:本次上机题目后两道较有难度,涉及题目信息的处理,如何将其转化为计算机语言是个难题,经过较长时间的翻阅资料与尝试才勉强完成,体现出我现在编程能力依然比较薄弱,但我也因此收获许多,明白了数组,容器vector,字符串string的简单的使用方法与语法规则,希望以后多加努力,查缺补漏,逐步提升。

  • 1
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值