Игра «Быки и коровы». Не могу до конца понять логику

Если например программа уже "нашла корову", то проверяет все остальные цифры и если находит "быка" засчитывает. Правильно ли это, или же если например я угадал все число и получил 4 "коровы" то "быков" уже не может быть? КОМЕНТАРИЕМ ОБОЗНАЧИЛ В КОДЕ ТУ ЧАСТЬ,КОТОРУЮ НАДО ПРОВЕРИТЬ(где происходит подсчет быков и коров).

Игра «Быки и коровы». Правила:

программа генерирует случайным образом 4-значное число;

пользователю предлагают угадать сгенерированное программой число;

за каждую угаданную пользователем цифру, стоящую на правильной позиции, он получает «корову»;

за каждую угаданную пользователем цифру, стоящую на неправильной позиции, он получает «быка»;

после каждого предположения пользователю должно выводиться количество «коров» и «быков», которые он заработал;

игра окончена тогда, когда пользователь угадал все цифры.

#include <iostream>
#include <ctime>
#include <Windows.h>
#include <conio.h>

using namespace std;

int main()
{
    srand(time(NULL));
    rand();
    setlocale(LC_ALL, "Rus");
    int rand_numb, num;
    int arr_rand_system[4] = {}, arr_inputs_sign[4] = {};
    int arr_count, count_cow, count_ox, count, attempt_num;
    bool continue_ = true;
    char n;

    cout << "Это игра \"Быки и коровы\"\n";
    cout << "программа генерирует случайное 4-значное число;\n"
        "вам необходимо угадать это число;\n"
        "за каждую угаданную вами цифру, стоящую на правильном месте, вы получите «корову»;\n"
        "если же цифра стоит на неправильном месте, вы получает «быка»;\n"
        "вы победите тогда когда угадаете все число.\n";

    
    while (continue_ != false)
    {
        arr_count = 0, count_cow = 0, count_ox = 0, count = 0, attempt_num = 0;
        srand(time(NULL));
        rand();

        rand_numb = (1000 + rand() % 9000);
        for (int i = 1000; i >= 1; i /= 10)
        {
            arr_rand_system[arr_count] = (rand_numb / i) % 10;
            arr_count++;
        }
        while (count != 4)
        {
            count_cow = 0, count_ox = 0, count = 0;
            while (true)
            {
                cout << "\n\nВведите 4-значное число: ";
                cin >> num;
                if (cin.fail() || num < 1000 || num > 9999)
                {
                    cin.clear();
                    cin.ignore(32767, '\n');
                    cout << "Вы ввели недопустимое число. Попробуйте еще раз\n";
                }
                else break;
            }
            arr_count = 0;
            for (int i = 1000; i >= 1; i /= 10)
            {
                arr_inputs_sign[arr_count] = (num / i) % 10;
                arr_count++;
            }





            for (int i = 0; i < 4; i++) // логика игры 
            {
                for (int j = 0; j < 4; j++)
                {
                    if (arr_rand_system[i] == arr_inputs_sign[j] && i == j) // подсчет коров
                    {
                        count_cow++;
                        count++;
                        continue;
                    }
                    else if (arr_rand_system[i] == arr_inputs_sign[j] && i != j) // подсчет быков
                        count_ox++;
                }
            }
            


                cout << count_cow << (count_cow == 1 ? " корова, " : (count_cow == 0 ? " коров, " : " коровы, "));
                cout << count_ox << (count_ox == 1 ? " бык\n" : (count_ox == 0 ? " быкoв\n" :" быка\n"));
                attempt_num++;
        }
        auto name_attempt = (attempt_num == 1 ? " попытка." : 
(attempt_num > 1 && attempt_num < 5 ? " попытки." : " попыток."));
        cout << "\n\nПоздравляю, вы выиграли. На это у вас ушло " << attempt_num 
<< name_attempt << "\nХотите продолжить ? Если да - нажмите Enter, нет - любую другую клавишу";
        if (!_kbhit())
        {
            n = _getch();
            if (n == 13)
                continue_ = true;
            else
                continue_ = false;
        }
    }
    
    

    return 0;
}

Ответы (2 шт):

Автор решения: Zhihar

как по мне код очень усложнён

как вижу его я:

  1. можно работать не с числом, а со строкой, в которую переводится число

  2. соответственно пользователь вводит цифру (переводится в букву) и позицию

таким образом общий код должен выглядеть так:

массив использованных цифр

int digits[10] 

может содержать значения 0 (цифра не использована), 1 (цифра использована, не в неправильной позиции), 2 (цифра использована в правильной позиции)

кол-во коров = 0
кол-во быков = 0

цикл пока кол-во коров + кол-во быков меньше кол-ву цифр в числе:
    запрашиваем у пользователя цифру и позицию

    если цифра раньше уже выбиралась (т.е. 1 или 2 в массиве digits) - переходим на начало цикла

    проверяем соответствует ли цифра цифре в числе в нужной позиции (одно сравнение буквы и буквы в строке)

    если буквы совпадают:
        кол-во коров ++
        для цифры выставляем в массиве digits значение 2

    если буквы не совпадают, то ищем букву в строке и если находим:
        кол-во быков ++
        для цифры выставляем в массиве digits значение 1

    выводим информацию о коровах и быках
→ Ссылка
Автор решения: Damir Hakimof
#include <iostream>
#include <vector>
#include <algorithm>
#include <random>
#include <string>
#include <ctime>

using namespace std;

string generateSecretNumber(int N) {
    vector<char> digits = {'0', '1', '2', '3', '4', '5', '6', '7', '8', '9'};
    shuffle(digits.begin(), digits.end(), mt19937(time(0)));
    
    string secret;
    for (int i = 0; i < N; ++i) {
        secret += digits[i];
    }
    return secret;
}

pair<int, int> countBullsAndCows(const string& secret, const string& guess) {
    int bulls = 0, cows = 0;
    
    for (int i = 0; i < secret.size(); ++i) {
        if (secret[i] == guess[i]) {
            ++bulls;
        } else if (secret.find(guess[i]) != string::npos) {
            ++cows;
        }
    }
    
    return {bulls, cows};
}

int main() {
    int N;
    cout << "Enter length (1-10): ";
    cin >> N;
    
    if (N < 1 || N > 10) {
        cerr << "Incorrect length!\n";
        return 1;
    }
    
    string secret = generateSecretNumber(N);
    string guess;
    int attempts = 0;
    
    cout << "Загадано число из " << N << " уникальных цифр. Угадайте его!\n";
    
    while (true) {
        cout << "Ваша попытка: ";
        cin >> guess;
        
        if (guess.size() != N) {
            cout << "Число должно быть длины " << N << "!\n";
            continue;
        }
        
        bool hasDuplicate = false;
        for (int i = 0; i < N; ++i) {
            for (int j = i + 1; j < N; ++j) {
                if (guess[i] == guess[j]) {
                    hasDuplicate = true;
                    break;
                }
            }
            if (hasDuplicate) break;
        }
        
        if (hasDuplicate) {
            cout << "Цифры не должны повторяться!\n";
            continue;
        }
        
        attempts++;
        auto [bulls, cows] = countBullsAndCows(secret, guess);
        
        cout << "Быки: " << bulls << ", Коровы: " << cows << endl;
        
        if (bulls == N) {
            cout << "Поздравляем! Вы угадали число за " << attempts << " попыток.\n";
            break;
        }
    }
    
    return 0;
}
→ Ссылка