『C/C++』Eg5: Imprimir reloj de arena

Esta pregunta requiere que escribas un programa para imprimir el símbolo dado en la forma de un reloj de arena. Por ejemplo, dado 17 "*", se requiere imprimir en el siguiente formato

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

La llamada "forma de reloj de arena" significa que cada línea genera un número impar de símbolos; los centros de los símbolos en cada línea están alineados; el número de símbolos en dos líneas adyacentes difiere en 2; el número de símbolos primero disminuye de grande a pequeño a 1, y luego aumenta en orden de pequeño a grande; Los números son iguales.

Dado cualquier número de N símbolos, no es necesariamente posible formar exactamente un reloj de arena. Se requiere que el reloj de arena impreso pueda usar tantos símbolos como sea posible.

Formato de entrada:

La entrada da 1 entero positivo N (≤1000) y un símbolo en una línea, separados por espacios.

Formato de salida:

Primero imprima la forma de reloj de arena más grande hecha de los símbolos dados y finalmente imprima la cantidad de símbolos no utilizados que quedan en una línea.

Muestra de entrada:

19 *

Salida de muestra:

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

respuesta:

Presumiblemente, cuando muchos amigos vieron esta pregunta por primera vez, pensaron que era muy simple y fácil de comenzar, pero cuando realmente lo pensaron, descubrieron que todavía era un poco difícil comenzar. Así que ahora explicaré mi pensamiento y la solución a esta pregunta ~

Desglose de la primera parte.

En primer lugar, este "reloj de arena" es simétrico hacia arriba y hacia abajo. Primero podemos encontrar cuántas capas hay por encima del medio (incluida la capa intermedia), y después de encontrar el número de capas superiores, restar uno, que es el número de capas inferiores. capas.
Usamos el método de resta del número total para encontrar el número de capas de arriba:
inserte la descripción de la imagen aquí
excepto por la primera vez (es decir, restando el medio) que es uno, los demás se restan todos por 2*i, y se requiere contar para cada resta. Sigue disminuyendo hasta que x sea un número negativo y el conteo se detenga.
Por ejemplo: 14 *
donde x es 14, la primera vez x=14-1=13; cuenta=1; la
segunda vez x=13-2x3=7; cuenta=2;
la tercera vez x=7-2x5=- 3 <0
salta fuera del bucle, porque la cuenta es 2, por lo que hay dos capas por encima.
Dado que restar la primera capa y restar varias capas es el doble de pequeño, escribe una capa y varias capas por separado.
A partir de esta idea, el código es el siguiente:

int Count(int x)
{
    
    
    int flag = 1, count = 1, i = 3;
    if (x < 7)//一层
        return 1;
    else//多层
    {
    
    
        x -= 1;//先减去中间层
        while (flag)
        {
    
    
            x -= 2 * i;
            if (x >= 0)
            {
    
    
                flag = 1;
                count++;
            }
            else
                flag = 0;
            i += 2;
        }
    }
    return count;
}

Aquí, se calcula el conteo de la capa superior y el número de la capa inferior es conteo-1;


Segunda parte: Impresión

mitad superior

Después de encontrar el número de capas aquí, comience a pensar en imprimir.
La impresión se divide en espacios y *. Aquí utilizo tablas para mostrar las conexiones entre las distintas partes.
Como solo necesita imprimir el espacio antes de cada capa *,
![Insertar descripción de la imagen aquí](https://img-blog.csdnimg.cn/11efb1b893864fd6b35df406f852a38f.png

El formulario es el siguiente:

para(j=0;j<cuenta;j++) número de espacios
j=0 0
j=1 1
j=2 2
re=n norte

Así que el código para imprimir espacios es el siguiente:

for (i = 0; i < count; i++)
{
    
    
    for (j = 0; j < i; j++)
        printf(" ");
}

Ahora consideremos la parte de imprimir *, sigue siendo la misma, la forma es la siguiente:

para(j=0;j<cuenta;j++) el número de *
j=0 2*cuenta-1
j=1 2*(cuenta-1)-1
j=2 2*(cuenta-2)-1
re=n 2*(cuenta-j)-1

Así que el código es el siguiente:

int k = count;
for (i = 0; i < count; i++)
{
    
    
    for (j = 0; j < 2 * k - 1; j++)
    {
    
    
        printf("%c", c);
    }
    k--;
}

Ok, hasta ahora, la primera mitad del reloj de arena está completa~


mitad inferior

Como de costumbre, veamos primero la parte del espacio, como se muestra en la figura a continuación,
inserte la descripción de la imagen aquí
aquí podemos usar fórmulas matemáticas para encontrar el número de espacios en la primera capa, y los espacios en cada capa a continuación solo deben basarse en el número de espacios en la capa anterior -1.Can.
Encuentra el número de espacios en la primera capa:
el número de espacios en la primera capa = (usa el número de '*' en la última capa - el número de '*' en la primera capa)/2
cómo encontrar el número de '*' en la última capa, use solo la fórmula anterior: 2*count-1,
por lo que el código para imprimir espacios es el siguiente:

int l=0;
l = count * 2 - 1;
l = (l - 3) / 2;
for (i = 0; i < count - 1; i++)
{
    
    
    for (j = 0; j < l; j++)
        printf(" ");
    l -= 1;
}

Bien, después de imprimir el número de espacios en la mitad inferior, imprimamos el * en la mitad inferior. Aquí es muy simple, ya que el número de * en la primera capa es 3, que permanece sin cambios, la siguiente capa solo necesita agregar 2 a la base original.
Entonces, el código para imprimir '*' es el siguiente:

int n = 3;
for (i = 0; i < count - 1; i++)
{
    
    
    for (j = 0; j < n; j++)
    {
    
    
        printf("%c", c);
    }
    n += 2;
}

En este punto, la impresión está completa, y ahora solo se trata de generar la cantidad de símbolos no utilizados ~


generar el número de símbolos no utilizados

Solo necesita contar cada impresión* en la función de impresión.

int Printc(int count, char c)
{
    
    
    int count1 = 0;
    for (i = 0; i < count; i++)
    {
    
    
        for (j = 0; j < 2 * k - 1; j++)
        {
    
    
            printf("%c", c);
            count1++;
        }

    }
    for (i = 0; i < count - 1; i++)
    {
    
    

        for (j = 0; j < n; j++)
        {
    
    
            printf("%c", c);
            count1++;
        }
    }
}

El código total es el siguiente:

#define _CRT_SECURE_NO_WARNINGS 1
#include<stdio.h>
int Count(int x)
{
    
    
    int flag = 1, count = 1, i = 3;
    if (x < 7)
        return 1;
    else
    {
    
    
        x -= 1;
        while (flag)
        {
    
    
            x -= 2 * i;
            if (x >= 0)
            {
    
    
                flag = 1;
                count++;
            }
            else
                flag = 0;
            i += 2;
        }
    }
    return count;
}

int Printc(int count,char c)
{
    
    
    int i = 0, j = 0, k = 0, l = 0, n = 3;
    int count1 = 0;
    l = count * 2 - 1;
    l = (l - 3) / 2;
    k = count;
    for (i = 0; i < count; i++)
    {
    
    
        for (j = 0; j < i; j++)
            printf(" ");
        for (j = 0; j < 2 * k - 1; j++)
        {
    
    
            printf("%c", c);
            count1++;
        }
        printf("\n");
        k--;
    }
    for (i = 0; i < count - 1; i++)
    {
    
    
        for (j = 0; j < l; j++)
            printf(" ");
        for (j = 0; j < n; j++)
        {
    
    
            printf("%c", c);
            count1++;
        }
        printf("\n");
        l -= 1;
        n += 2;
    }
    return count1;
}

int main()
{
    
    
    int x = 0, y = 0;
    char c = 'a';
    scanf("%d %c", &x, &c);
    y = Count(x);
    int F=Printc(y,c);
    printf("%d\n", x-F);
    return 0;
}



Muy bien ~ Este es el final de las preguntas de intercambio de lenguaje C de hoy, hasta la próxima

Supongo que te gusta

Origin blog.csdn.net/hsjsiwkwm/article/details/130948067
Recomendado
Clasificación