PTA 打印沙漏 C++

本题要求你写个程序把给定的符号打印成沙漏的形状。例如给定17个“*”,要求按下列格式打印

*****
 ***
  *
 ***
*****

所谓“沙漏形状”,是指每行输出奇数个符号;各行符号中心对齐;相邻两行符号数差2;符号数先从大到小顺序递减到1,再从小到大顺序递增;首尾符号数相等。

给定任意N个符号,不一定能正好组成一个沙漏。要求打印出的沙漏能用掉尽可能多的符号。

输入格式:

输入在一行给出1个正整数N(≤1000)和一个符号,中间以空格分隔。

输出格式:

首先打印出由给定符号组成的最大的沙漏形状,最后在一行中输出剩下没用掉的符号数。

输入样例:

19 *

输出样例:

*****
 ***
  *
 ***
*****
2

 [代码]

#include <iostream>
using namespace std;

class solution {
public:
	solution(int i, char c) :num(i),key(c) {}
	void print() {
		if (num == 0) {
			cout << endl << 0 << endl;
			return;
		}
		int i = 1, cnt = 0, extra;
		for (; cnt < num; i += 2) 
			if (i != 1) cnt += i * 2;
			else cnt++;
		if (cnt != num)
			cnt -= (i -= 2) * 2;
		i -= 2;
		extra = num - cnt;
		printsand(i, i);
		cout << extra << endl;
	}
	void printsand(int i, int a) {
		if (i == 1) {
			for (int j = a / 2 - i / 2; j > 0; j--)
				cout << ' ';
			cout << key << endl;
			return;
		}
		for (int j = a / 2 - i / 2; j > 0; j--) 
			cout << ' ';
		for (int j = i; j > 0; j--)
			cout << key;
		cout << endl;
		printsand(i - 2, a);
		for (int j = a / 2 - i / 2; j > 0; j--)
			cout << ' ';
		for (int j = i; j > 0; j--)
			cout << key;
		cout << endl;
	}
private:
	int num;
	char key;
};

int main() {
	int i;
	cin >> i;
	char c;
	cin >> c;
	solution sandglass(i, c);
	sandglass.print();
	return 0;
}

打印沙漏用了递归,这当然不是最好的解法,但是我脑子有限。。。

### PTA 沙漏图案 Java 打印 实现代码 以下是基于题目描述和参考资料中的要求,提供一个完整的解决方案。该方案能够接收输入的字符数量 `N` 和指定符号,并按照沙漏形状打印输出。 #### 解决方案说明 为了完成此任务,需要遵循以下逻辑: 1. 计算可以构成的最大层数以及剩余未使用的字符数。 2. 构建每一层所需的星号数目,形成上半部分和下半部分的沙漏结构。 3. 将构建好的字符串逐行打印出来,并在最后一行显示剩余字符的数量。 下面是具体的实现代码: ```java import java.util.Scanner; public class Sandglass { public static void main(String[] args) { Scanner scanner = new Scanner(System.in); int N = scanner.nextInt(); // 总字符数 char symbol = scanner.next().charAt(0); // 给定符号 int k = 1; // 层数计数器 while (5 * k * k - 4 * k + 1 <= N) { // 寻找最大可能的k值 k++; } k--; // 调整到实际可用的最大k值 int usedSymbols = 5 * k * k - 4 * k + 1; // 已使用字符总数 int remainingSymbols = N - usedSymbols; // 剩余字符数 StringBuilder resultBuilder = new StringBuilder(); for (int i = 0; i < k; i++) { String line = generateLine(symbol, k, i); // 生成当前行的内容 resultBuilder.append(line).append("\n"); } for (int i = k - 2; i >= 0; i--) { String line = generateLine(symbol, k, i); // 生成倒置的部分 resultBuilder.append(line).append("\n"); } System.out.println(resultBuilder.toString()); // 输出沙漏图案 System.out.println(remainingSymbols); // 输出剩余字符数 } private static String generateLine(char symbol, int k, int row) { int spacesCount = k - row - 1; int symbolsInRow = 2 * row + 1; StringBuilder sb = new StringBuilder(); for (int j = 0; j < spacesCount; j++) { sb.append(' '); // 添加前导空格 } for (int j = 0; j < symbolsInRow; j++) { sb.append(symbol); // 添加符号 } return sb.toString(); } } ``` #### 关键点解析 上述代码实现了以下几个功能模块: - **计算最大层数**:通过循环找到满足条件的最大正整数值 \( k \),使得总字符数不超过输入的 \( N \)[^1]。 - **生成每行内容**:利用辅助函数 `generateLine()` 来动态调整每行的空白符与符号比例[^2]。 - **上下两部分拼接**:分别处理沙漏的上部和下部,最终组合成完整图案[^3]。 - **输出结果**:先打印整个沙漏图案,再单独一行展示剩余字符数[^4]。 --- ###
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值