强行刷段位第二天

版权声明:本文为博主原创文章,未经博主允许不得转载。 https://blog.csdn.net/Mirror1997/article/details/85759067

今天是刷段位第二天了,好几天没下过楼,我真是太懒了。。。

一会去买点东西。

有点想剪头发了,长发难打理还爱掉。。。女生秃头可不好看。

做题做题。。。


模拟第一题:

题目:

现代数学的著名证明之一是Georg Cantor证明了有理数是可枚举的。他是用下面这一张表来证明这一命题的: 1/1 1/2 1/3 1/4 1/5 … 2/1 2/2 2/3 2/4 … 3/1 3/2 3/3 … 4/1 4/2 … 5/1 … … 我们以Z字形给上表的每一项编号。第一项是1/1,然后是1/2,2/1,3/1,2/2,…

输入描述:

整数N(1≤N≤10000000)

输出描述:

扫描二维码关注公众号,回复: 4789797 查看本文章

表中的第N项

样例输入:

7

样例输出:

1/4

我的答案:

写这篇博客的时候才注意到这是一道模拟题,可是我是找规律写的诶。

反正做出来了,还挺顺当。就是之前把c--;和sumc=sumc-4*c-1;写反了,不过稍微思考一下就能改过来了。不是很难找的bug。

一厢情愿的认为这种比单纯模拟的方式更快些?至少是比递归要节省的。

另外,注释要跟上啊,本来我写代码的变量名就爱乱写。。。以后工作了自己写的东西同事看不懂就不好了。。

于是这道题,我加了注释,虽然只有四个字。但是我一厢情愿的认为灰常有用,哈哈。

如下:

#include <iostream>
using namespace std;

int main()
{
	int c=0,sumc=0,resc=0;
	int m=1,summ=0,resm=0;
	int n=0;
	cin>>n;
	
	while(sumc<n)//分子 
	{
		sumc=sumc+4*c+1;
		c++;
	}
	c--;
	sumc=sumc-4*c-1;
	if(n-sumc<=2*c+1)
	    resc=n-sumc;
	else  resc=4*c+2-n+sumc;
	
	while(summ<n)//分母 
	{
		summ=summ+4*m-1;
		m++;
	}
	m--;
	summ=summ-4*m+1;
	if(n-summ<=2*m)
	    resm=n-summ;
	else  resm=4*m-n+summ;
	
	cout<<resc<<"/"<<resm;
	
	return 0;
	
 } 

模拟第二题:

题目:

小明玩一个数字游戏,取个n行n列数字矩阵(其中n为不超过100的奇数),数字的填补方法为:在矩阵中心从1开始以逆时针方向绕行,逐圈扩大,直到n行n列填满数字,请输出该n行n列正方形矩阵以及其的对角线数字之和.

输入描述:

n(即n行n列)

输出描述:

n+1行,n行为组成的矩阵,最后一行为对角线数字之和

样例输入:

3

样例输出:

5 4 3
6 1 2
7 8 9
25

我的答案:

又是小明。

感觉我做模拟题还行啊,应该是模拟类的比较容易。我想开心又不敢开心,因为每次我要因为什么开心的时候生活总是会给我一巴掌告诉我,你高兴得太早了(笑哭)。

这一题实打实的用了模拟,100行代码完成。看到有大佬57行解决。可是仔细看了下,也是模拟,把输出之类的都夹在矩阵建立里了,总体来讲换汤不换药。

我写东西喜欢加换行,因为总是犯迷糊,加点换行看着清楚。

加了很多注释,这次的代码应该比较清楚了,以后再看的话应该看一眼想起来了。

如下:

#include <iostream>
using namespace std;

int main()
{
	int n;
	int i=0,j=0;   //实际的行列数
	int max_i=0,max_j=0;   //当前的行列数限制 
	int min_i=0,min_j=0;   //当前的行列数限制 
	int num=1;   //当前进行到的数值 
	int sum=0;  //对角线和 
	
	cin>>n;

	int arr[100][100]={0};      //都赋值0 	
	i=(n-1)/2;     //赋初值 
	j=(n-1)/2;
	max_i=(n-1)/2;
	max_j=(n-1)/2;
	min_i=(n-1)/2;
	min_j=(n-1)/2;	

	while(i!=(n-1) || j!=(n-1))  //创造蛇形矩阵 
	{
		while(j<=max_j)
		{
			arr[i][j]=num;
			j++;
			num++;
		}
		
		while(i>=min_i)
		{
			arr[i][j]=num;
			i--;
			num++;
		}
		
		while(j>=min_j)
		{
			arr[i][j]=num;
			j--;
			num++;
		}
		
		while(i<=max_i)
		{
			arr[i][j]=num;
			i++;
			num++;
		}
		
		while(j<=max_j)
		{
			arr[i][j]=num;
			j++;
			num++;
		}
		
	max_i++;
	max_j++;
	min_i--;
	min_j--;			
	}	

	arr[n-1][n-1]=num;  //最后一个元素赋值


	i=0;
	j=0;
	while(i<n && j<n)  //求主对角和 
	{
		sum=sum+arr[i][j];
		i++;
		j++; 
	 }

	 i=0;
	 j=n-1;
	 while(i<n && j>=0)  //求副对角和
	 {
	 	sum=sum+arr[i][j];
	 	i++;
	 	j--;
	  }	
	sum=sum-arr[n/2][n/2];


    for(i=0;i<n;i++)  //输出数组 
    {
    	for(j=0;j<n;j++)
	    {
	      cout<<arr[i][j]<<" ";		
		}
		cout<<endl;
	}

	cout<<sum;  //输出对角和 

	return 0;
 } 

明天加油~就算明天的很难也要迎难而上~不以物喜,不以己悲,如是而已

买东西去啦!


东西也没买上,被妈妈骂了一顿。。。

更年期的女人太可怕,一点就着,不点自燃(瑟瑟发抖.jpg)

我只能瞬间变身乌龟,不动不玩不说话……正好适合刷题。刷着刷着就不委屈了……

下面是今天下午做的题:


数论入门第一题:

题目:

输入二个正整数x0,y0(2<=x0<100000,2<=y0<=1000000),求出满足下列条件的P,Q的个数

条件:  1.P,Q是正整数

           2.要求P,Q以x0为最大公约数,以y0为最小公倍数.

试求:满足条件的所有可能的两个正整数的个数

输入描述:

二个正整数x0,y0

输出描述:

满足条件的所有可能的两个正整数的个数

样例输入:

3 60

样例输出:

4

我的答案:

这道题有点迷,其实就强行求就好。该输入的输入,该辗转相除就辗转相除。最小公倍数就是最大公约数和两个数与公约数的商的乘积。使劲加换行的话50行也能搞定了。

过程中出现两个问题:

1.对于两个数来说,12和15、15和12,这两个是不一样的。之前看了半天,把每一对都输出来看也没搞明白为什么正确结果是4,我的结果是2。后来突然想到这一点,果断乘2,果然问题就是在这了。

2.不知道为什么,DEVC++中可以在int k; cin>>k;后int arr[k]; 没有问题。但是Codevs不行,编译出错。编译器不同,有时候会有一些不能编译的情况。所以这些语句要记在心里,一旦编译出错,马上就想到应该是这里的问题,并且要知道怎么改。我把这称作脆弱行。有问题就看看是不是脆弱行出问题了吧~

代码如下:

#include <iostream>
using namespace std;

int  search(int a,int b)//辗转相除 
{
	if(a%b==0) return  b;
	else search(b,a%b);
} 

int main()
{
	int x=0,y=0;
	int k=0,i=0,j=0;
	int sum=0;
	cin>>x>>y;
	
	k=y/x;
	int arr[k]={0};
    int t=0,m=0;
    
  for(i=0;i<k;i++)
     {
     	arr[i]=x*(i+1);
	  } 
 
  for(i=0;i<k;i++)
    {
    	for(j=i+1;j<k;j++)
    	{
    		t=search(arr[i],arr[j]);
    		cout<<arr[i]<<"&"<<arr[j]<<":"<<t<<endl;
     		m=t*(arr[i]/t)*(arr[j]/t);
    		if(x==t  &&  y==m)
    		 {
    		 	sum++;

			  } 
		}
	}
  
	cout<<sum*2; 
	
	return 0;
	
 } 

数论入门第二题:

题目:

求两个数A和B的最大公约数。 1<=A,B<=2^31-1

输入描述:

两个整数A和B

输出描述:

最大公约数gcd(A,B)

样例输入:

8 12

样例输出:

4

我的答案:

又写了一题,完全就是上一题的一部分,最大公约数,一个辗转相除就可以了。

不知道为什么总是把最复杂的问题放在第一个。

辗转相除如下:

#include <iostream>
using namespace std;

int  search(int a,int b)
{
	if(a%b==0) return  b;
	else search(b,a%b);
}
 
int main()
{
	int x=0,y=0;
	int res=0;
	cin>>x>>y;
	
    res=search(x,y);
    cout<<res;
    
	return 0;	
 } 

数论入门第三题:

题目:

质数又称素数指在一个大于1的自然数中,除了1和此整数自身外,不能被其他自然数整除的数

素数在数论中有着很重要的地位。比1大但不是素数的数称为合数。1和0既非素数也非合数。质数是与合数相对立的两个概念,二者构成了数论当中最基础的定义之一。基于质数定义的基础之上而建立的问题有很多世界级的难题,如哥德巴赫猜想等。算术基本定理证明每个大于1的正整数都可以写成素数的乘积,并且这种乘积的形式是唯一的。这个定理的重要一点是,将1排斥在素数集合以外。如果1被认为是素数,那么这些严格的阐述就不得不加上一些限制条件。

概念

只有1和它本身两个约数的自然数,叫质数(Prime Number)。(如:由2÷1=2,2÷2=1,可知2的约数只有1和它本身2这两个约数,所以2就是质数。与之相对立的是合数:“除了1和它本身两个约数外,还有其它约数的数,叫合数。”如:4÷1=4,4÷2=2,4÷4=1,很显然,4的约数除了1和它本身4这两个约数以外,还有约数2,所以4是合数。)
100以内的质数有2,3,5,7,11,13,17,19,23,29,31,37,41,43,47,53,59,61,67,71,73,79,83,89,97,在100内共有25个质数。
注:(1)1既不是质数也不是合数。因为它的约数有且只有1这一个约数。
(2)2和3是所有素数中唯一两个连着的数 .

输入描述:

第一行输入一个正整数n,n<=30000

输出描述:

如果该数是质数,则输出\t

否则输出\n

样例输入:

输入样例1

13

输入样例2

8

样例输出:

样例输出1

\t

样例输出2

\n

数据范围及提示:

c或c++的初学者注意,"\"的意思

我的答案:

这道题的麻烦还真不在设计算法上。这道题学到的东西如下吧:

1.\n是换行符;\\n第一个\是转义字符,也就是说,\n输出换行而\\n在屏幕上显示\n。

2.前几天在某乎上看到一个高中生自称证明了哥德巴赫猜想。果然人类还是把一切事情想的太乐观。很早之前就知道,文字越少的题目越难做。而题目的字越多说明条件越多。最难证明的往往是那些普适的。越是特定情况下的越容易。

比如这道题,题目墨迹了这么多,其实很容易。

而哥德巴赫猜想恰恰是证明“1+1”,这才是最困难也是最精妙的。陈景润花了多少心血才证明了“1+2”,想证明“1+1”,是要积淀和天赋的。

初生牛犊不怕虎,这份朝气是棒的。

但是也要学会脚踏实地,不要妄想洋洋洒洒一张草稿纸,就被人奉为神人。

倒不是觉得年轻人,狂放一些有什么。就只是在知乎发文章,还要来张预告,新年到来之际准时准点给大家奉上自己的证明,就觉得年纪小,除了有些未出象牙塔表演欲,更多的是冒冒失失的可爱。

若真是成了事,还不抓紧投个大的。。。哪有心思发知乎。。。傻孩子。。。

这种可爱,是鲁莽,但也是搞学术的人的一份希望吧。

我的话好多。

代码:

#include <iostream>
using namespace std;
int main()
{
    int n;
    int flag=0,i=0;
    cin >>n; 
    for(i=2;i<n;i++)
    {
        if(n%i==0)
        {
            flag=1;
            break;
        }
    }
    
    if(flag==1) cout<<"\\n";
    else cout<<"\\t";
    
    return 0;
}

今天就到这吧,去做运动了。

明天要加油。

不能开拓,至少也要努力,多看懂一些前人令人拍案叫绝的杰作呀~

拜拜~

猜你喜欢

转载自blog.csdn.net/Mirror1997/article/details/85759067