亲宝软件园·资讯

展开

C语言打印菱形 C语言打印菱形实例详解

marwi_study 人气:0

前言

打印菱形这道题对于初学编程者来说简直是噩梦,曾经我就是栽在这上面的,后来编程编多了之后对打印菱形也觉得不再那么难了,去年在公众号写了一篇推送是关于打印菱形的,觉得对一些师弟师妹还是有所帮助的,今天就把这道题分享出来。

以下是我遇到的各种各样的菱形:

普通菱形,输入n,输出n行n列的菱形

难度系数:♥

n行空心菱形,输入n,输出n行空心菱形

难度系数:♥♥

n行挖空菱形,输入n,输出n行n列空格菱形

难度系数:♥♥♥

n行数字菱形,输入n,输入n行数字从外到内递增的数字菱形

难度系数:♥♥♥♥

有边框空心菱形,输入n,输出n行带有边框的空心菱形

难度系数:♥♥♥♥♥

首先我们要明确这是一个随着n的大小改变的菱形,所以我们肯定要用到循环,并且循环的次数与n有关。如果题目要求是输出n行,那我们的循环就是0(n-1)或者1n;如果要求是输出(2n+1)行,那我们的循环就0-2n或者1~(2n+1)即可。(后面以输出n行为例分析)

第一个是普通的实心菱形,循环n行大家都懂,问题就在列要怎样循环。难道是看出来的吗?不错,我就是通过看得出来的循环次数。具体怎么看呢?

根据图直接看有点难度,所以我们根据各行数据来看


我们需要将整个菱形分成四块来考虑,从上到下空格的个数先从n/2递减到0后递增到n/2,而行循环因子i又从0递增到n,故自然可联想到用i与n/2来表示空格个数。因为空格个数是非负数,所以我们引进绝对值|n/2-i|表示空格个数。打完空格之后,我们就要正式用 ' * '打印菱形了。通过观察我们发现 * 号的个数为奇数,并且变化规律跟空格正好相反,所以号个数即是-2*(空格个数)+1+C(常数)=-2*(空格个数)+C(常数),通过观察我们发现这个常数C正好是n/2。于是第一种菱形就可以顺利完成了!

第二个是空心菱形,与实心菱形相似,可看成在实心菱形上再打了一个空格菱形。由于每行的号数不多,并且可以看到号正好位于空格菱形的外围,所以我们可以将打印号放在打印空格菱形前后顺便打印,即在打印空格菱形之前打号,打印完空格菱形之后再打印号。同样,我们将相关数据列出来然后观察规律。号前空格与实习菱形一致,而我们发现n-2|n/2-i|-2的值除了首尾两行外,其他都与空格菱形的空格个数一致,而首尾两行是-1表示在该处不需打空格反而需要退一个格,但由于我们当前位置为号,而退格后依旧要打号,所以我们可以直接判断是否为第一行或最后一行,是则少打印一个号即可。

第三个是挖空菱形,该菱形是上述两个的合体,我们可以看成把一个实心菱形的各个字符替换成另一种字符,再插入一个空心菱形。所以我们把该菱形分成输出空心菱形前后号和输出空心菱形两部分。通过数据对比,我们不难发现,输出空心菱形前后号的数据与实心菱形输出号前空格个数一致,然后就是输出一个空心菱形,最后要记得在输出空心菱形之后输出空心菱形之后的号,根据对称可知,空心菱形后号个数与空心菱形前号一致。

第四个是数字菱形,该菱形的特点是数字从外到内逐层递增。我们发现该菱形中轴线数字的变化规律是先从1递增到(n+1)/2,然后再递减到1,并且每一行的数字也是从1递增到中轴线,再递减到1,因此我们要找到中轴线所在的位置(方便判断循环因子是否到达中轴线)。通过列数据我们发现中轴线所在位置(j从0开始循环)为n/2-|n/2-i|,所以在每一行中我们的数字加到“j==n/2-|n/2-i|”处时应该转成递减,所以我们引进要填充的数字k,在每一行开始时k为1,在j从0到n/2-|n/2-i|-1中,k逐次递增,在j从n/2-|n/2-i|到n-2*|n/2-i|-1中k递减。然后将打印星号改为打印数字即可。

第五个是边框空心菱形。从名字可知,该菱形由边框和空心菱形组成,我们可以将边框和空心菱形分开来考虑。第一行和最后一行为边框,可直接用从0到n-1打印号实现。左右边框在每一行的开头和结尾打印号即可实现。中间即是空心菱形的领域,基本上跟打印空心菱形一样,只是要注意被边框覆盖的地方空格和号要省略。

将打印空格和打印号分开考虑,通过数字之间的关系特点,运用循环完成菱形的打印。

由于菱形是对称的,所以绝对值是最好的数据描述工具,要巧妙地运用绝对值,将对称部分的循环用同一个带有绝对值的表达式表示出来。

值得注意的是n/2为整数除,所以不会得到小数,也不是四舍五入。

中轴线所在位置(j从0开始循环)为n/2-|n/2-i|。

//挖空菱形
 for(i=0;i<n;i++){
  for(j=0;j<abs(n/2-i);j++)
   printf("*");
  printf("*");
  for(j=0;j<n-2*abs(n/2-i)-2;j++)
   printf(" ");
  if(j!=0)
   printf("*");
  for(j=0;j<abs(n/2-i);j++)
   printf("*");
  printf("\n");
 }
 printf("\n");
 //边框菱形
 for(i=0;i<n;i++){
  if(i==0||i==n-1){
   for(j=0;j<n;j++)
    printf("*");
   printf("\n");
  }
  else{
   printf("*");
   for(j=0;j<abs(n/2-i)-1;j++)
    printf(" ");
   if(j!=0)
    printf("*");
   for(j=0;j<n-2*abs(n/2-i)-1;j++)
    printf(" ");
   if(j!=0)
    printf("*");
   for(j=0;j<abs(n/2-i)-1;j++)
    printf(" ");
   if(j!=0)
    printf("*");
   printf("\n");
  }
 }
 //数字菱形
 for(i=0;i<n;i++){
  int k=1;
  for(j=0;j<abs(n/2-i);j++)
   printf(" ");
  for(j=0;j<n-2*abs(n/2-i);j++){
   printf("%d",k);
   if(j<n/2-abs(n/2-i))
    k++;
   else
    k--;
  }
  printf("\n");
 }
 //实心菱形
 for(i=0;i<n;i++){
  for(j=0;j<abs(n/2-i);j++)
   printf(" ");
  for(j=0;j<n-2*abs(n/2-i);j++)
   printf("*");
  printf("\n");
 }
 printf("\n");
 //空心菱形
 for(i=0;i<n;i++){
  for(j=0;j<abs(n/2-i);j++)
   printf(" ");
  printf("*");
  for(j=0;j<n-2*abs(n/2-i)-2;j++)
   printf(" ");
  if(j!=0)
   printf("*");
  printf("\n");
 }

总结

加载全部内容

相关教程
猜你喜欢
用户评论