Помогите найти ошибки

VASA, описалово составил как можно подробнее

#include <iostream>
#include <cstdlib>
#include <windows.h>

const char* colors[] = { "color 2", "color 4", "color 6", "color 9" }; // константный массив для хранение цветов
const int milliseconds = 200;       // константная переменная - начальное значение миллисекунд

void coord(int x, int y);   // прототип функции - псевдокоординаты
void getFill(int width, char fill);  // прототип функции отображения строки с заданным заполнителем

int main()
{
    const int width = 10;   // ширина строки
    const int height = 7;   // кол-во строк
    const char fill = '*';  // заполнитель

    int counter = 10;        // кол-во циклов
    int x, y;               // координаты

    do {
        x = 0, y = 0;       // установка псевдокоординат в 0

        for (int j = 0; j < 2; j++) {   // отображение верхних двух фигур 
            system(::colors[j]);        // установка цвета, на каждом цикле вызываем новый цвет

            for (int i = 0; i < height; i++){   // отображение фигуры высотою в height
                coord(x, y);                    // псевдопозиционирование строк (каждая строка отображается с заданным отступом по х)
                getFill(width, fill);           // отображение строки заданой длины и заданым заполнителем
            }

            x += width;     // смещаем отображение фигуры на длину строки

            Sleep(::milliseconds * (j + 1));    // аргумент функции значение миллисекунд на каждом цикле увеличенное на 200
            system("cls");                      // очистка экрана
        }

        for (int k = 2; k < 4; k++) {   // отображение нижних двух фигур
            system(::colors[k]);        // установка цвета

            x -= width;                 // смещаем положение псевдокурсора на позицию х + widht, после первого цикла позиция курсора = х + 2width

            coord(0, height);   // позиционирование псевдокурсора

            for (int i = 0; i < height; i++){   // отображение фигуры высотою в height
                coord(x, y);                    // псевдопозиционирование строк
                getFill(width, fill);           // отображение строки заданой длины
            }

            Sleep(::milliseconds * (k + 1));    // аргумент функции значение миллисекунд на каждом цикле увеличенное на 200
            system("cls");                      // очистка экрана
        }

    } while (counter--);    // уменьшение кол-ва циклов до нуля (к каждом цикле отображаются четыре фигуры)

    return 0;
}

// функция псевдопозиционирования
// параметры функции координаты х и у
void coord(int x, int y)
{
    for (int j = 0; j < y; j++){    // по у смещаемся вниз
        std::cout << "\n";
    }

    for (int i = 0; i < x; i++){    // по х смещаемся вправо
        std::cout << " ";
    }
}

// функция отображения строки заданной длины и заполнителя
void getFill(int width, char fill)
{
    for (int i = 0; i < width; i++) {  // отображение заполнителя в строке
        std::cout << fill;
    }

    std::cout << '\n';  // переход на новую строку
}

beginner, можно таки я еще покритикую твой код? Во-первых, изменение позиции курсора размазано по трем функциям: coord, get_fill и main. Во-вторых, функция coord используется как универсальный костыль: для затыкания дыр. На самом деле, переменные x и y функции main ни как не связаны с реальным положением курсора. А аргументы функции coord имеют семантически разное значение: аргумент x — абсолютная позиция курсора, а аргумент y — относительная. Перед вызовом функции вывода строки прямоугольника вызывается функция coord, но второй аргумент всегда 0, поскольку сдвиг по вертикали происходит в get_fill и нужно сдвигаться только по горизонтали. Зато перед выводом второй пары прямоугольников функция coord вызывается только для позиционирования по вертикали. Обнуление координат курсора происходит в main при вызове cls. Если уж был выбран такой алгоритм работы функции main, то надо было писать две отдельные функции: для сдвига по горизонтали и для сдвига по вертикали. Но это все равно не спасает положение.

Что б не говорили, что критиковать легко, предлагаю свой вариант, который реализует «шаг 1» из моего предыдущего поста.

#include <iostream>
#include <cstdlib>
#include <windows.h>

const char* colors[] = { "color 2", "color 4", "color 6", "color 9" };
const DWORD milliseconds = 200;

const int LINE_LEN = 80;  // размер буфера строки

const int width = 20;
const int height = 10;


//Функция для рисования прямоугольника.
//Аргументы:
//  x, y - координаты левого верхнего угла прямоугольника
//  w, h - ширина и высота прямоугольника
//  fill - необязательный аргумент, символ-заполнитель

void draw_rect(int x, int y, int w, int h, char fill = '*') {
    char line[LINE_LEN];      // массив для хранения строки прямоугольника

    system("cls");            // очистить экран (и сбросить в 0 текущие координаты вывода)

    // формирование строки для рисования одной строки прямоугольника
    int i, j;                 // переменны циклов должны существовать и после выхода из циклов
    for (i = 0; i < x; i++)   // добавить в массив нужное количество пробелов
        line[i] = ' ';
    for (j = 0; j < w; j++)   // добавить в массив нужное количество символов-заполнителей
        line[i+j] = fill;
    line[i+j] = '\0';         // добавить маркер конца строки

    for (i = 0; i < y; i++)   // отпозиционироваться по вертикали
        std::cout << "\n";

    // отрисовка прямоугольника
    for (i = 0; i < h; i++)    // вывести нужное количество строк прямоугольника
        std::cout << line << "\n";
}

int main()
{
    int counter = 4;
    DWORD ms = milliseconds;   // задержка перед рисованием нового прямоугольника
    bool trigger = true;       // переключатель увеличения/уменьшения задержки

    do {
        for (int i = 0; i < 4; i++) {
            system(colors[i]);
            draw_rect((i < 2 ? i % 2 : (3 - i) % 2) * width, i / 2 * height, width, height);
            if (trigger) {
                ms += milliseconds;    // увеличение задержки,
                trigger = ms < 1600;   // пока задержка меньше 1600мс
            }
            else {
                ms -= milliseconds;    // уменьшение задержки,
                trigger = ms <= 200;   // пока задержка больше 200мс
            }
            // std::cout << ms;     // тестовая печать текущего значения задержки
            Sleep(ms);
        }
    } while (counter--);

    // очистить экран и вернуть цвет вывода по умолчанию
    system("cls");
    system("color 7");

    return 0;
}

beginner, можно таки я еще покритикую твой код?
[skipped]
Но это все равно не спасает положение.

Это называется «ошибка при проектировании». Самая тяжёлая разновидность ошибок. Проще закрасить, чем отскребать. Что, собственно, Фтьiкай и сделал.

и еще вопрос. Как изменить кол-во проходов в цикле?
P.S. вопрос к beginnerу

VASA, если вы имеете в виду цикл do ... while ();

int counter = 10;        // кол-во циклов
int x, y;               // координаты

do {
    x = 0, y = 0;       // установка псевдокоординат в 0

    for (int j = 0; j < 2; j++) {   // отображение верхних двух фигур 
        system(::colors[j]);        // установка цвета, на каждом цикле вызываем новый цвет

        for (int i = 0; i < height; i++){   // отображение фигуры высотою в height
            coord(x, y);                    // псевдопозиционирование строк (каждая строка отображается с заданным отступом по х)
            getFill(width, fill);           // отображение строки заданой длины и заданым заполнителем
        }

        x += width;     // смещаем отображение фигуры на длину строки

        Sleep(::milliseconds * (j + 1));    // аргумент функции значение миллисекунд на каждом цикле увеличенное на 200
        system("cls");                      // очистка экрана
    }

    for (int k = 2; k < 4; k++) {   // отображение нижних двух фигур
        system(::colors[k]);        // установка цвета

        x -= width;                 // смещаем положение псевдокурсора на позицию х + widht, после первого цикла позиция курсора = х + 2width

        coord(0, height);   // позиционирование псевдокурсора

        for (int i = 0; i < height; i++){   // отображение фигуры высотою в height
            coord(x, y);                    // псевдопозиционирование строк
            getFill(width, fill);           // отображение строки заданой длины
        }

        Sleep(::milliseconds * (k + 1));    // аргумент функции значение миллисекунд на каждом цикле увеличенное на 200
        system("cls");                      // очистка экрана
    }

} while (counter--);    // уменьшение кол-ва циклов до нуля (к каждом цикле отображаются четыре фигуры)

то нужно изменить значение переменной counter.

Проще закрасить, чем отскребать. Что, собственно, Фтьiкай и сделал.

Это не Фтьiкай сделал, это я начал закрашивать.
Все не было времени, а на днях сел и попробовал решить задачу поставленную VASA не закрашивая ее.
Решил реализовать класс, который может выполнять визуальные эффекты над фигурами (по умолчанию, ТЗ выдал VASA, псевдо вращение прямоугольника с изменением цвета). Класс, который отвечает за вывод на консоль реализован с помощью системозависимых команд Windows.
Вот реализация: исходники здесь.

PS: Протестить полностью не успел, т.ч. если есть баги пишите ;)

1-ая проблема: не считывает данные с клавиатуры на 3-ем scanf, а сразу завершает прог-у. 2-ая проблема: выводит не считываемые данные, а набор символов. Информация должна выводиться в форме таблицы.

#include <stdio.h>
#include <iostream>

    using namespace std;

    int main()
    {
        setlocale(LC_CTYPE,"");
        char name1[12], name2[12], name3[12];
        char type1, type2, type3;
        double price1, price2, price3;
        unsigned short min1, min2, min3;
        printf("1. Введите: Наименование товара, Тип товара, Цена за 1 шт (грн), Минимальное количество в партии >");
        scanf("%14s %c %5.2f %-3d",name1, &type1, &price1, &min1);
        printf("2. Введите: Наименование товара, Тип товара, Цена за 1 шт (грн), Минимальное количество в партии >");
        scanf("%14s %c %5.2f %-3d",name2, &type2, &price2, &min2);
        printf("3. Введите: Наименование товара, Тип товара, Цена за 1 шт (грн), Минимальное количество в партии >");
        scanf("%14s %c %5.2f %-3d",name3, &type3, &price3, &min3);
        cout<<"\n------------------------------------------------------------------------------\n";
        cout<<"|Прайс-лист                                                                  |\n";
        cout<<"|----------------------------------------------------------------------------|\n";
        cout<<"|Наименование товара |Тип товара |Цена за 1 шт (грн) |Минимальное количество |\n";
        cout<<"|                    |           |                   |в партии               |\n";
        cout<<"|----------------------------------------------------------------------------|\n";
        printf("| %14s | %c | %5.2f | %-3d |\n",name1, type1, price1, min1);
        cout<<"|----------------------------------------------------------------------------|\n";
        printf("| %14s | %c | %5.2f | %-3d |\n",name2, type2, price2, min2);
        cout<<"|----------------------------------------------------------------------------|\n";
        printf("| %14s | %c | %5.2f | %-3d |\n",name3, type3, price3, min3);
        cout<<"|----------------------------------------------------------------------------|\n";
        cout<<"|Примечание: К – канцтовары, О - оргтехника                                  |\n";
        cout<<"------------------------------------------------------------------------------\n";
        cout <<"\nPress Enter to continue…";
        cin.get();
        return 0;
    }

ERD,

  1. Тщательно изучи документацию по scanf в части форматов и типов данных. Правильный формат будет выглядеть так: ""%11s %c %lf %hu".

  2. Выход за границу массива. Под переменные nameN выделено по 12 байт, а scanf по твоему формату может вводить 14.

  3. Для таких наборов данных лучше использовать массивы. А ещё лучше массив записей.
    И ввод данных делать в цикле.

  4. Прочитай статью «Символы кириллицы в консоли Windows» во избежание вопроса почему наименование товара выводится неправильно.

Внимание! Это довольно старый топик, посты в него не попадут в новые, и их никто не увидит. Пишите пост, если хотите просто дополнить топик, а чтобы задать новый вопрос — начните новый.

Ответить

Вы можете использовать разметку markdown для оформления комментариев и постов. Используйте функцию предпросмотра для проверки корректности разметки.

Пожалуйста, оформляйте исходный код в соответствии с правилами разметки. Для того, чтобы вставить код в комментарий, скопируйте его в текстовое поле ниже, после чего выделите то, что скопировали и нажмите кнопку «код» в панели инструментов. Иначе ваш код может принять нечитаемый вид.

Либо производите оформление кода вручную, следующим образом:

``` #include <iostream> using namespace std; int main() { // ... } ```

Предпросмотр сообщения

Ваше сообщение пусто.