#c #for-loop #if-statement
#c #для цикла #if-statement
Вопрос:
Напишите программу, которая печатает лестницу размером n.
Я не прошел через все тестовые случаи и не понимаю, где я допустил ошибку.
Это мой код:
void staircase(int n) {
char a[n][n];
for(int i = 0; i < n; i ) {
for(int j = 0; j < n; j ) {
if((i j) > ((n / 2) 1)) {
a[i][j] = '#';
printf("%c", a[i][j]);
} else {
printf(" ");
}
}
printf("n");
}
}
Учитывая входные данные
6
Ожидаемый результат
#
##
###
####
#####
######
Объяснение:
Лестница выровнена по правому краю, состоит из символов # и пробелов и имеет высоту и ширину n=6
.
Комментарии:
1. Пожалуйста, предоставьте ожидаемый результат и выходные данные вашей программы здесь.
2. Если вы используете язык C, кого вы помечаете C ?
3. Какой тестовый пример вы провалили
4. testcase с
n == 1
должен печатать пробел или восьмиугольник?5. @Tarik Это скрытые тестовые случаи, в которых произошел сбой кода. Видимые тестовые примеры пройдены.
Ответ №1:
Проблема в условии
if((i j) > ((n / 2) 1))
Это должно быть
if(j >= n - i - 1) // or if(i j >= n - 1)
Чтобы упростить это, я бы создал вспомогательную функцию. Кроме того, нет необходимости в VLA a[n][n]
, который вы даже ни для чего не используете.
void repeat_char(int x, char ch) {
for(int i=0; i < x; i) putchar(ch);
}
void staircase(int n) {
for(int i = 1; i <= n; i) {
repeat_char(n - i, ' '); // or printf("%*s", n - i, "");
repeat_char(i, '#');
putchar('n');
}
}
Комментарии:
1. Спасибо, условие было ошибочным. Ваше предложение помогло 🙂
2. Код, который вы написали, намного проще, но я новичок и думаю, что потребуется время, чтобы написать такие чистые и простые коды.
3. @sb7 Может потребоваться некоторое время, чтобы определить, какие части вы можете выделить и поместить в простые функции, которые выполняют всего одну маленькую вещь, такую как
repeat_char
функция, но всегда будьте в поиске этих частей. 🙂
Ответ №2:
Вам не нужна ваша a
переменная, чтобы делать то, что вам нужно. Вот пример достижения того, чего вы хотите:
void staircase(unsigned n)
{
for (unsigned i = 0; i < n; i) {
for (unsigned j = 0; j < (n - i - 1); j)
printf(" ");
for (unsigned j = 0; j < (i 1); j)
printf("#");
printf("n");
}
}
Первый цикл предназначен для покрытия каждой строки, затем внутри него вы создаете цикл, который обрабатывает пробелы перед фактическими #
символами, и, наконец, вы создаете цикл, обрабатывающий отображение символов.
Комментарии:
1. просто замечание: использовать printf для вывода одного символа стоит зря, иначе вы можете попросить printf вывести ожидаемый отступ для первого #, а не делать это самостоятельно
2. Спасибо за замечание, однако разве любой современный компилятор не сделал бы оптимизацию самостоятельно?
3. на этом уровне это не «оптимизация», вы просите слишком многого 😉
4. Вы были бы удивлены! Просто проверил сам, и кажется, что 9.3 делает это! Вот процесс компиляции и результат сборки: paste.ubuntu.com/p/zCzyNPCvQP ; В строках 148, 158 и 165 C-код
printf
заменен наputchar
‘s5. в некотором смысле это печально, в любом случае, вы не можете предположить, что у вас есть такой компилятор, лучше сделайте сами, не так ли?
Ответ №3:
Есть гораздо более простой способ сделать это, чем то, что вы пытаетесь сделать:
#include <malloc.h>
#include <stdio.h>
#include <stdlib.h>
int main(void) {
const int n = 6;
char* str = malloc(sizeof(*str)*(n 1));
if (str == NULL) {
printf("Somthing wrong with memory!n");
return 1;
}
memset(str, ' ', n);
str[n] = '';
for(int i = n - 1; i > -1; i--) {
str[i] = '#';
puts(str); //or maybe printf who cares
}
free(str);
return 0;
}