原题:
输入输出格式
输入格式:
输入两个整数x,n(表示从周x算起,经过n天,n在long int范围内)。
输出格式:
输出一个整数,表示小鱼累计游泳了多少公里。
输入输出样例
输入样例#1:
3 10
输出样例#1:
2000
方法一:分情况找规律,主要有以下几种情况
①x<6&&x+n<=6 => 250*n
用程序实现:
if(x<6&&x+n<=6) printf("%d",250*n);
②x<6 && x+n7 => 250*(n-1)
x<6 && x+n8 => 250*(n-2)
~
x<6 && x+n14 => 250*(n-3)
x<6 && x+n15 => 250*(n-4)
…
可以看出这个部分的规律可以用循环实现
for(i=1;1;i++)
{
if(x<6&&(x+n)==7*i)
{
printf("%d",250*(n-(2*i-1)));
break;
}
else if(x<6&&(x+n)==(7*i+1))
{
printf("%d",250*(n-2*i));
break;
}
else break;
}
③x<6 && 8<x+n<=13 => 250*(n-2)
~
x<6 && 15<x+n<=20 => 250*(n-4)
~
x<6 && 22<x+n<=27 => 250*(n-6)
…
还是可以明显看出这段规律可以用循环写出:
for(i=1;1;i++)
{
printf("%d\n",i);
if(x<6&&(x+n)>(7*i+1)&&(x+n)<=(7*i+6))
{
printf("%d",250*(n-2*i));
break;
}
else break;
}
④x==6 && x+n<=8 => 0
if(x==6&&(x+n)<=8) printf("0");
⑤x6 && 8<x+n<=13 =>250*(n-2)
~
x6 && 15<x+n<=20 =>250*(n-2)
~
x==6 && 22<x+n<=27 =>250*(n-2)
…
可以看出这里可以直接归纳入上一段程序,即将x<6改为x<=6即可
for(i=1;1;i++)
{
printf("%d\n",i);
if(x<=6&&(x+n)>(7*i+1)&&(x+n)<=(7*i+6))
{
printf("%d",250*(n-2*i));
break;
}
else break;
}
但分析问题时最好将这两种情况分开分析,否则易混淆
⑥x6 && x+n14 =>250*(n-3)
~
x6 && x+n21 =>250*(n-5)
~
x6 && x+n28 =>250*(n-7)
…
程序如下:
for(i=2;1;i++)
{
if(x==6&&(x+n)==7*i)
{
printf("%d",250*(n-(2*i-1)));
break;
}
else break;
}
⑦x==7 && x+n<=8 =>0
if(x==7&&x+n<=8) printf("0");
⑧x7 && 8<x+n<=13 =>250*(n-1)
~
x7 && 15<x+n<=20 =>250*(n-3)
~
x==7 && 22<x+n<=27 =>250*(n-5)
…
这一段用程序实现如下:
for(i=1;1;i++)
{
if(x==7&&(x+n)>(7*i+1)&&(x+n)<=7*i+6)
{
printf("%d",250*(n-i));
break;
}
else break;
}
⑨x7 && x+n14 =>250*(n-2)
~
x7 && x+n21 =>250*(n-4)
~
x7 && x+n28 =>250*(n-6)
…
程序如下:
for(i=2;1;i++)
{
if(x==7&&(x+n)==7*i)
{
printf("%d",250*(n-i));
break;
}
else break;
}
⑩x7 && (x+n)15 =>250*(n-3)
~
x7 && (x+n)22 =>250*(n-5)
~
x7 && x+n29 =>250*(n-7)
…
程序:
for(i=2;1;i++)
{
if(x==7&&(x+n)==(7*i+1))
{
printf("%d",250*(n-(i+1)));
break;
}
else break;
对于这种方法有以下几点说明:
(1)每一段一个for只是为了说明问题,如果直接把它们按顺序放在一起构成整个程序是会出错的,比如第一个假设i=0时,x,n不满足两个条件,就会直接跳出循环。而原意是希望用循环找出满足条件的,如果循环完了,都没有满足的才跳出这一个循环,进入下面的判断。
但如果去掉最后的break;又会使得程序在遇到x,n不满足两个条件时,无限循环,跳不出循环。
(2)对于x与n的含义要正确理解,例如
x<6 && 8<x+n<=13 => 250*(n-2)
x<6表示开始游泳时间为周一~周五中任意一天;n表示的是从这一天开始经过了n天,值得注意的是包括了周x当天自身;对于x+n的理解:例x=1,n=7则x+n=8,表示从周一开始算,过了7天所以x+n表示把本周周天刚好过完;所以8<x+n<=13表示结束的那一天在下周一到下周五之间,此时只过了上一个双休日,所以它游了n-2天,也就游了250*(n-2)公里。
(3)需要考虑x<6,x=6,x=7三种大的情况,而每一种又要考虑x+n(结束的那一天在周一~周五,周六,周天并把当天过完)三种情况。
(4)正确代码如下,其中将原来每个for中的else break;语句删去,并放入了一个for循环,就能实现一段满足不了可以进行后续的判断的功能,并且能实现没有x,n与当下的i配对时i+1再从头开始判断的循环功能。所以对于之前有的i从2开始循环有的从1开始循环的问题不需担心,对于输入的确定的x,n一定输出的只有一个解,也就只有那一段程序能实现,不会在不对应的程序段因为i的不同而满足并输出。所以放心的把各个程序段放进一个for中。
/*正确代码*/
#include<stdio.h>
int main()
{
int x,n;
int i;
scanf("%d%d",&x,&n);
if(x<6&&x+n<=6) printf("%d",250*n);
for(i=1;1;i++)
{
if(x<6&&(x+n)==7*i)
{
printf("%d",250*(n-(2*i-1)));
break;
}
if(x<=6&&(x+n)>(7*i+1)&&(x+n)<=(7*i+6))
{
printf("%d",250*(n-2*i));
break;
}
if(x==6&&(x+n)==7*i)
{
printf("%d",250*(n-(2*i-1)));
break;
}
if(x==7&&(x+n)>(7*i+1)&&(x+n)<=7*i+6)
{
printf("%d",250*(n-(2*i-1)));
break;
}
if(x==7&&(x+n)==(7*i+1))
{
printf("%d",250*(n-(2*i-1)));
break;
}
if(x==7&&(x+n)==7*i)
{
printf("%d",250*(n-(2*i-2)));
break;
}
if(x==6&&(x+n)<=8)
{
printf("0"); break;
}
if(x==7&&x+n<=8)
{
printf("0");
break;
}
else if(x<6&&(x+n)==(7*i+1))
{
printf("%d",250*(n-2*i));
break;
}
};
}
方法二:简单易懂的程序:
#include<stdio.h>
main()
{
int x,n,i,s=0;
scanf("%d%d",&x,&k);
for(i=1;i<=k;i++)
{
if(x!=6&&x!=7)
{
s+=250;
}
else if(x==6)
{
x=7;
}
else if(x==7)
{
x=1;
}
}
printf("%d",s);
}
理解:非周末直接计数,周末直接跳过,用for直接实现。