题目介绍:
题目分析:n=1时
n=2 时
实质就是把n=1的三角形 向左下 右下复制了一遍
n=3时
实质就是把 n=2时的三角形向 左下 右下复制
n=4时
实质就是把 n=3时的三角形 向左下右下 复制了一次
综上题目分析:知 输入n时,就是循环n-1次 每次循环的内容就是 把循环前的三角形向 左下 右下 去复制。
故我们考虑采用 二维数组进行 整体的复制 更为方便。
有题目知 n的范围在[1,8] 上述 最大三角形的 底边为 2^(n-1) 个三角形
例如(n=4时 底边为8个三角形)
底边共占有 3*(2^(n-1))*2 - 1=767 (不止有* 还有 空格) (n=8时最大)
斜边 占有 3*(2^(n-1))*2 (不带空格的)
所以数组可定义为 arr[800][800] 既满足所需要的空间
代码解析:
y表示最顶上的那个*的位置 例如n=3时;
y=3*4=12 底边带空格 一共3*4*2-1个位置 中 间位置即为y
数组我以arr[1][1]为第一个 后面打印的时候
该部分就是初始化第一个小三角形的的图形 1 2 3表示行数 y表 示列数
表示循环几次 即要复制几次三角形
因为每循环一次,我们需要复制的三角形需要变大,所以引入 fanwei变量进行控制。
数组最开始我们就从arr[1][1]开始布局的 所以打印就从一开始
注意:行数列数不一样的 因为列数里面包含了空格!!!
上述图坐标图进行了说明
这部分就比较简单了 打印个尾巴即可 因为我们上述有y 故尾巴在y处打印即可。
源代码展示:
//超级圣诞树解析 n=1 一个小三角形
// n=2 循环一次 把上述小三角形 复制到左下 右下 形成一个大三角形
// n=3 循环两次 把上述大三角形 复制到左下 右下 形成 更大的三角形 一次类推………………
#include<stdio.h>
#include<math.h>
int main()
{
int n = 0;
char arr[800][800] = { 0 };
while ((scanf("%d", &n)) != EOF)
{
int y = 3 * pow(2, n - 1); //y表示最上面那个小三角的顶点的纵坐标 一行y列 数列这里我从1开始排布
arr[1][y] = '*';
arr[2][y-1]= '*';
arr[2][y+1]= '*';
arr[3][y-2]= '*';
arr[3][y+2]= '*';
arr[3][y] = '*';
int i = 0;
for (i = 1; i <= n - 1; ++i)
{
int fanwei = 3 * pow(2, i - 1)-1;
for (int x1 = 1; x1 <= 1 + fanwei; ++x1) //往左下复制
{
for (int y1 = y - fanwei; y1 <= y + fanwei; ++y1)
arr[x1 + fanwei + 1][y1 - fanwei - 1] = arr[x1][y1];
}
for (int x1 = 1; x1 <= 1 + fanwei; ++x1) //往右下复制
{
for (int y1 = y - fanwei; y1 <= y + fanwei; ++y1)
arr[x1 + fanwei + 1][y1 + fanwei + 1] = arr[x1][y1];
}
}
//打印数组 来形成圣诞树
for (i = 1; i <= (3 * pow(2, n - 1)); ++i)
{
for (int j = 1; j <= (3 * pow(2, n - 1)*2 - 1); ++j)
{
if (arr[i][j] == '*')
printf("*");
else
printf(" ");
}
printf("\n");
}
// 打印尾巴
for (i = 1; i <= n; ++i)
{
for (int j = 1; j < y; ++j)
printf(" ");
printf("*");
printf("\n");
}
}
return 0;
}