Как этот код генерирует карту Индии?


этот код печатает карту Индии. Как это работает?

#include <stdio.h>
main()
{
    int a,b,c;
    int count = 1;
    for (b=c=10;a="- FIGURE?, UMKC,XYZHello Folks,
    TFy!QJu ROo TNn(ROo)SLq SLq ULo+
    UHs UJq TNn*RPn/QPbEWS_JSWQAIJO^
    NBELPeHBFHT}TnALVlBLOFAkHFOuFETp
    HCStHAUFAgcEAelclcn^r^rtZvYxXy
    T|S~Pn SPm SOn TNn ULo0ULo#ULo-W
    Hq!WFs XDt!" [b+++21]; )
    for(; a-- > 64 ; )
    putchar ( ++c=='Z' ? c = c/ 9:33^b&1);
    return 0;
}
2 159

2 ответа:

длинная строка - это просто двоичная последовательность, преобразованная в ASCII. Первый for утверждение b начните в 10, и [b+++21] после строки дает 31. Рассматривая строку как массив, смещение 31 является началом "реальных" данных в строке (вторая строка в приведенном примере кода). Остальная часть кода просто проходит через последовательность битов, Преобразуя 1 и 0 в !'s и пробелы и печать по одному символу за раз.

меньше запутанная версия:

#include "stdio.h"
int main (void) {
    int a=10, b=0, c=10;
    char* bits ="TFy!QJu ROo TNn(ROo)SLq SLq ULo+UHs UJq TNn*RPn/QPbEWS_JSWQAIJO^NBELPeHBFHT}TnALVlBLOFAkHFOuFETpHCStHAUFAgcEAelclcn^r^r\tZvYxXyT|S~Pn SPm SOn TNn ULo0ULo#ULo-WHq!WFs XDt!";
    a = bits[b];
    while (a != 0) {
        a = bits[b];
        b++;
        while (a > 64) {
            a--;
            if (++c == 'Z') {
                c /= 9;
                putchar(c);
            } else {
                putchar(33 ^ (b & 0x01));
            }
        }
    }
    return 0;
}

The странно умная часть находится в putchar заявления. Возьмите первый putchar. ASCII 'Z' это 90 в десятичной системе счисления, поэтому 90 / 9 = 10, который является символом новой строки. Во втором десятичное число 33-это ASCII для '!'. Переключение младшего бита 33 дает вам 32, что является ASCII для пространства. Это вызывает ! для печати b странно, а пустое место для печати b еще. Остальная часть кода-это просто там ходить "указатель"a через строку.

в основном, в строке run-length encoding изображения: чередующиеся символы в строке говорят, сколько раз рисовать пробел, и сколько раз рисовать восклицательный знак последовательно. Вот анализ различных элементов этой программы:

закодированная строка

первые 31 символ этой строки игнорируются. Остальные содержат инструкции по рисованию изображения. Индивидуальные характеры определяют сколько пробелов или восклицательных знаков рисовать последовательно.

внешний цикл for

этот цикл проходит через символы в строке. Каждая итерация увеличивает значение b и назначает следующий символ в строке a.

внутренний цикл for

этот цикл рисует отдельные символы и новую строку, когда она достигает конца строки. Количество нарисованных символов a - 64. Этот значение c идет от 10 до 90 и сбрасывается до 10 при достижении конца строки.

The putchar

это можно переписать как:

++c;
if (c==90) {       //'Z' == 90
    c = 10;        //Note: 10 == '\n'
    putchar('\n');
}
else {
    if (b % 2 == 0)
        putchar('!');
    else
        putchar(' ');
}

он рисует соответствующий знак, в зависимости от того,b четный или нечетный, или новая строка, когда это необходимо.