Вложенные циклы для создания спиральной фигуры в форме - PullRequest
0 голосов
/ 16 ноября 2018

Мне нужно сделать спиральный узор из звездочек *, используя вложенные петли для. Мне удалось сделать внешние линии, теперь я не знаю, как повторить меньшие завихрения в одном и том же месте. Что у меня должно быть:

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

Любая помощь будет принята с благодарностью.

Ответы [ 3 ]

0 голосов
/ 16 ноября 2018

Самый разумный подход - создать 2d массив, а затем заполнить его нужным *.

В качестве альтернативы, вы можете попытаться придумать логику «точно вовремя», чтобы избежать буфера. Это сложнее.

Я придумал подход, думая о спирали как о четырех разных треугольниках, которые образуют квадрат. Здесь я напечатал «a, b, c, d» для каждого из четырех треугольников, чтобы показать, что я имею в виду:

aaaaaaaaaac
          c
 baaaaaac c
 b      c c
 b baac c c
 b b dd c c
 b b    c c
 b dddddd c
 b        c
 dddddddddd  

В этом есть две хитрые части. Одним из них является правильное выравнивание диагоналей. Не так сложно с методом проб и ошибок. Другая сложная сторона заключается в том, что не все квадраты делятся на чередующиеся линии одинаково. Вы можете видеть в примере выше квадрат n=11, левая сторона смещена на единицу. Возможно, есть лучшее решение, но это попытка создать чередующиеся строки и столбцы.

n = 11;
for (int i = 0; i < n; i++)
{
    for (int j = 0; j < n; j++)
    {
        // top
        if (j > i - 2 && j < n - i && i % 2 == (n&1)) printf("a");
        // left
        else if (j < i - 1 && j < n - i && j % 2 == (n & 1)) printf("b");
        // right
        else if (j > n - i -1&& j > i && j % 2 == ((n+1) & 1)) printf("c");
        // bottom
        else if (j < i + 1 && j > n - i - 1 && i % 2 == ((n + 1) & 1)) printf("d");
        else printf(" ");
    }
    printf("\n");
}
0 голосов
/ 16 ноября 2018

После тщательного укромного зануда я придумал следующее:

#include <stdio.h>

void print_spiral(int size)
{
    for (int y = 0; y < size; ++y)
    {
        for (int x = 0; x < size; ++x)
        {
            // reflect (x, y) to the top left quadrant as (a, b)
            int a = x;
            int b = y;
            if (a >= size / 2) a = size - a - 1;
            if (b >= size / 2) b = size - b - 1;

            // calculate distance from center ring
            int u = abs(a - size / 2);
            int v = abs(b - size / 2);
            int d = u > v ? u : v;
            int L = size / 2;
            if (size % 4 == 0) L--;

            // fix the top-left-to-bottom-right diagonal
            if (y == x + 1 && y <= L) d++;

            printf((d + size / 2) % 2 == 0 ? "X" : " ");
        }

        printf("\n");
    }
}

Как уже упоминалось, может быть более интуитивно понятно выделить массив, представляющий сетку, и нарисоватьспираль в массив (внутри которого вы можете свободно перемещаться), затем распечатайте массив.Но в этом решении используется память O (1).

Его почти наверняка можно немного оптимизировать и упростить, но я «оставлю это как упражнение для читателя», поскольку я уже потратил слишком многовремя на это; -)


Обновление

Я не собираюсь тратить на это больше времени, но у меня была идея для второй попытки, что может результат в более простом коде.Если вы проверяете вывод во все больших размерах, появляется шаблон:

enter image description here

В каждом квадранте шаблон является регулярным и может быть легко закодирован.Я думаю, вам просто нужно тщательно классифицировать ( x , y ) координаты в один из четырех квадрантов, а затем применить соответствующий шаблон.

0 голосов
/ 16 ноября 2018

Я бы рекомендовал взглянуть на библиотеку NCurses .Он содержит множество методов для перемещения курсора в окне терминала, например mvaddch() и curs_set().

Здесь - это документ, который содержит все, что вам нужно знать о том, какиспользовать NCurses .

Однако , если вы не хотите использовать внешние библиотеки, вы можете определить двумерный массив из int s или bool s, а затем выведите *, где индекс равен 1 или true, соответственно.

Пример последнего:

#include <stdbool.h>  //You need to include this header file if you want to use 'bool's
...
//Using a 10x10 array for this example
bool stars[10][10] = { /* initialize the 2D array here */ };
...
//Get the length of a row
int rowLength = (sizeof stars[0]) / (sizeof stars[0][0]);

//Get the amount of rows
int rowAmount = (sizeof stars) / (sizeof stars[0]));

//Print the spiral using the array "stars"
for(int r = 0; r < rowAmount; r++){
    for(int c = 0; c < rowLength; c++){
        if(stars[r][c])
            printf("*");
        else
            printf(" ");
    }
    printf("\n");
}
...
...