C++ Small Straight (например, яхтзи или покер). 5 Бросок кубика (1234)/(2345)/(3456)

Я новичок в C++, и это для домашнего задания, но я застрял. У меня есть одна оставшаяся проблема, и тогда я закончил. Я не могу придумать алгоритм, который скажет, ввел ли пользователь небольшой стрит (1234), (2345) или (3456). Я знаю, как это сделать с помощью цикла, но можно ли не использовать цикл? Когда это было назначено, мы еще не узнали о петлях. Я думаю, что мы должны использовать только операторы if. Я начал кодировать для него (я написал, что могут быть кубики, но не могу понять, как пустить только 4 кубика прямо без массива и цикла). Я застрял! Пожалуйста помоги! Можете ли вы также проверить мой код и посмотреть, есть ли что-то не так.

Назначенная проблема:

Игра в покер с костями. (Вроде как Яхтзи)

• Попросите пользователя ввести 5 бросков кубиков (1-6) в любом порядке. Попросите пользователя ввести 5 цифр. Если какие-либо из них находятся за пределами диапазона от 1 до 6 включительно, просто завершите программу.

• Подсчитайте и распечатайте количество введенных единиц.

• Подсчитайте и напечатайте количество введенных двоек.

• Подсчитайте и напечатайте количество введенных троек.

• Подсчитайте и напечатайте введенное количество четверок.

• Подсчитайте и напечатайте количество введенных пятерок.

• Подсчитайте и напечатайте количество введенных шестерок.

• Скажите, есть ли три или более одинаковых костей.

• Скажите, есть ли четыре или более одинаковых костей.

• Скажите, есть ли пять одинаковых костей.

• Скажите, есть ли фулл-хаус, 3 одинаковых и 2 одинаковых.

• Сообщить, есть ли длинный стрит... 1 2 3 4 5 или 2 3 4 5 6

• Сообщить, есть ли небольшой стрит (1 2 3 4), (2 3 4 5) или (3 4 5 6)

Мой код:

int main(int argc, char** argv)
{
//
int Roll1, Roll2, Roll3, Roll4, Roll5;
int numberOf1s = 0, numberOf2s = 0, numberOf3s = 0, numberOf4s = 0, numberOf5s = 0, numberOf6s = 0;
bool TwoOfaKind = false;
bool ThreeOfaKind = false;
cout << "Roll 5 dice. Enter them below." << endl;
cout << "Roll 1: ";
cin >> Roll1;
cout << "Roll 2: ";
cin >> Roll2;
cout << "Roll 3: ";
cin >> Roll3;
cout << "Roll 4: ";
cin >> Roll4;
cout << "Roll 5: ";
cin >> Roll5;

if (Roll1 > 6 || Roll1 < 1 || Roll2 > 6 || Roll2 < 1 || Roll3 > 6 || Roll3 < 1 || Roll4 > 6 || Roll4 < 1 || Roll5 > 6 || Roll5 < 1 )
{
   exit(1);
}

if (Roll1 == 1)
{
    numberOf1s += 1;
}
if (Roll2 == 1)
{
    numberOf1s += 1;
}
if (Roll3 == 1)
{
    numberOf1s += 1;
}
if (Roll4 == 1)
{
    numberOf1s += 1;
}
if (Roll5 == 1)
{
    numberOf1s += 1;
}
cout << "There are " << numberOf1s << " ones." << endl;

if (Roll1 == 2)
{
    numberOf2s += 1;
}
if (Roll2 == 2)
{
    numberOf2s += 1;
}
if (Roll3 == 2)
{
    numberOf2s += 1;
}
if (Roll4 == 2)
{
    numberOf2s += 1;
}
if (Roll5 == 2)
{
    numberOf2s += 1;
}
cout << "There are " << numberOf2s << " twos." << endl;

if (Roll1 == 3)
{
    numberOf3s += 1;
}
if (Roll2 == 3)
{
    numberOf3s += 1;
}
if (Roll3 == 3)
{
    numberOf3s += 1;
}
if (Roll4 == 3)
{
    numberOf3s += 1;
}
if (Roll5 == 3)
{
    numberOf3s += 1;
}
cout << "There are " << numberOf3s << " threes." << endl;

if (Roll1 == 4)
{
    numberOf4s += 1;
}
if (Roll2 == 4)
{
    numberOf4s += 1;
}
if (Roll3 == 4)
{
    numberOf4s += 1;
}
if (Roll4 == 4)
{
    numberOf4s += 1;
}
if (Roll5 == 4)
{
    numberOf4s += 1;
}
cout << "There are " << numberOf4s << " fours." << endl;

if (Roll1 == 5)
{
    numberOf5s += 1;
}
if (Roll2 == 5)
{
    numberOf5s += 1;
}
if (Roll3 == 5)
{
    numberOf5s += 1;
}
if (Roll4 == 5)
{
    numberOf5s += 1;
}
if (Roll5 == 5)
{
    numberOf5s += 1;
}
cout << "There are " << numberOf5s << " fives." << endl;

if (Roll1 == 6)
{
    numberOf6s += 1;
}
if (Roll2 == 6)
{
    numberOf6s += 1;
}
if (Roll3 == 6)
{
    numberOf6s += 1;
}
if (Roll4 == 6)
{
    numberOf6s += 1;
}
if (Roll5 == 6)
{
    numberOf6s += 1;
}
cout << "There are " << numberOf6s << " sixes." << endl << endl;
if (numberOf1s == 2 || numberOf2s == 2 || numberOf3s == 2 || numberOf4s == 2 || numberOf5s == 2 || numberOf6s == 2)
{
    TwoOfaKind = true;
}
if (numberOf1s == 3 || numberOf2s == 3 || numberOf3s == 3 || numberOf4s == 3 || numberOf5s == 3 || numberOf6s == 3)
{
    cout << "Yes three of a kind!" << endl;
    ThreeOfaKind = true;
}
else
{
    cout << "No three of a kind" << endl;
}

if (numberOf1s == 4 || numberOf2s == 4 || numberOf3s == 4 || numberOf4s == 4 || numberOf5s == 4 || numberOf6s == 4)
{
    cout << "Yes four of a kind!" << endl;
}
else
{
    cout << "No four of a kind" << endl;
}

if (numberOf1s == 5 || numberOf2s == 5 || numberOf3s == 5 || numberOf4s == 5 || numberOf5s == 5 || numberOf6s == 5)
{
    cout << "Yes five of a kind!" << endl;
}
else
{
    cout << "No five of a kind" << endl;
}

//
if (TwoOfaKind == true && ThreeOfaKind == true)
{
     cout << "Yes Full House!" << endl;
}
else
{
    cout << "No Full House" << endl;
}

//
if (Roll1 == Roll2 && Roll2 == Roll3 && Roll3 == Roll4 && Roll4 == Roll5)
{
    cout << "No Long Straight" << endl;
}
else
{
    if (((Roll1 >= 1 && Roll1 < 6) && (Roll2 >= 1 && Roll2 < 6) && (Roll3 >= 1 && Roll3 < 6) && (Roll4 >= 1 && Roll4 < 6) && (Roll5 >= 1 && Roll5 < 6)) && (Roll1 != Roll2 && Roll2 != Roll3 && Roll3 != Roll4 && Roll4 != Roll5))
    {
        cout << "Yes Long Straight!" << endl;
    }
    else if (((Roll1 > 1 && Roll1 <= 6) && (Roll2 > 1 && Roll2 <= 6) && (Roll3 > 1 && Roll3 <= 6) && (Roll4 > 1 && Roll4 <= 6) && (Roll5 > 1 && Roll5 <= 6)) && (Roll1 != Roll2 && Roll2 != Roll3 && Roll3 != Roll4 && Roll4 != Roll5))
    {
        cout << "Yes Long Straight!" << endl;
    }
    else
    {
        cout << "No Long Straight" << endl;
    }

//***HELP ME HERE PLEASE!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!***
if (Roll1 == Roll2 && Roll2 == Roll3 && Roll3 == Roll4 && Roll4 == Roll5)
{
    cout << "No Small Straight" << endl;
}
else
{
    if (((Roll1 > 1 && Roll1 <= 4) && (Roll2 > 1 && Roll2 <= 4) && (Roll3 > 1 && Roll3 <= 4) && (Roll4 > 1 && Roll4 <= 4) && (Roll5 > 1 && Roll5 <= 4)) && (Roll1 != Roll2 && Roll2 != Roll3 && Roll3 != Roll4 && Roll4 != Roll5))
    {
        cout << "Yes Small Straight!" << endl;
    }
    else if (((Roll1 > 1 && Roll1 <= 5) && (Roll2 > 1 && Roll2 <= 5) && (Roll3 > 1 && Roll3 <= 5) && (Roll4 > 1 && Roll4 <= 5) && (Roll5 > 1 && Roll5 <= 5)) && (Roll1 != Roll2 && Roll2 != Roll3 && Roll3 != Roll4 && Roll4 != Roll5))
    {
        cout << "Yes Small Straight!" << endl;
    }
    else if (((Roll1 > 2 && Roll1 <= 6) && (Roll2 > 2 && Roll2 <= 6) && (Roll3 > 2 && Roll3 <= 6) && (Roll4 > 2 && Roll4 <= 6) && (Roll5 > 2 && Roll5 <= 6)) && (Roll1 != Roll2 && Roll2 != Roll3 && Roll3 != Roll4 && Roll4 != Roll5))
    {
        cout << "Yes Small Straight!" << endl;
    }
   else
   {
       cout << "No Small Straight" << endl;
   }
}

return 0;

}


person R4g323    schedule 06.03.2015    source источник
comment
мой маленький прямой код внизу кода   -  person R4g323    schedule 06.03.2015
comment
Вот хорошая версия Yahtzee для C/C++ на Code Review, она есть несколько хороших советов о том, как преобразовать код, похожий на ваш, в функции   -  person tsundoku    schedule 06.03.2015
comment
@tsundoku: я бы не назвал это хорошей версией: например, код броска кубика повторяется 5 раз.   -  person MSalters    schedule 06.03.2015
comment
@MS изменяет дальше ответ, код броска кубика реорганизован в один цикл, сразу после: Теперь мы видим, что блок, запрашивающий повторный бросок кубика X, в основном также все тот же, за исключением номера кубика.   -  person tsundoku    schedule 06.03.2015


Ответы (2)


Я решил переписать вашу программу, которая реорганизует большую часть кода, а также решит вашу проблему. Обратите внимание, я предполагал, что вы используете c++, но не обязательно c++11.

#include <iostream>
#include <cstdlib>
#include <string>
using namespace std;

int main()
{
    int straight_checker = 0;
    int rolls[5] = {0}, num_count[6] = {0};

    // use char * die_names[6] if c
    string die_names[6] = {"ones", "twos", "threes", "fours", "fives", "sixes"};
    bool two_kind = false, three_kind = false, four_kind = false, five_kind = false;

    cout << "Roll 5 dice. Enter them below." << endl;
    for(unsigned int i = 0; i < sizeof(rolls) / sizeof(int); ++i)
    {
        cout << "Roll " << i + 1 << ": ";
        cin >> rolls[i];

        if(rolls[i] < 1 || rolls[i] > 6)
        {
            exit(1);
        }
        else
        {
            num_count[rolls[i] - 1]++;
            // This will set a binary "1" at the location rolls[i] - 1, easy way to check straights
            straight_checker ^= (-1 ^ straight_checker) & (1 << (rolls[i] - 1));
        }
    }

    for(unsigned int i = 0; i < sizeof(num_count) / sizeof(int); ++i)
    {
        cout << endl << "There are " << num_count[i] << " " <<die_names[i];

        // If you are using c++11, then use std::find outside loop
        switch(num_count[i])
        {
            case 2:
                two_kind = true;
                break;
            case 3:
                three_kind = true;
                break;
            case 4:
                four_kind = true;
                break;
            case 5:
                five_kind = true;
                break;
        }
    }

    cout << endl;

    if(four_kind) cout << "Yes four of a kind!" << endl;
    if(five_kind) cout << "Yes five of a kind!" << endl;
    if(two_kind && three_kind) cout << "Yes Full House!" << endl;
    else
    {
        if(three_kind) cout << "Yes three kind" << endl;
        else if(two_kind) cout << "Yes two kind" << endl;
    }

    // 31 in binary is 011111, and 62 is 111110 (ie 5 straight 1s)
    if(straight_checker == 31 || straight_checker == 62)
    {
        cout << "Yes long straight!" << endl;
    }
    // 47 in binary is 101111, 30 is 011110, 61 is 111101, etc (ie 4 straight 1s)
    if(straight_checker == 15 || straight_checker == 47 || straight_checker == 30 || straight_checker == 60 || straight_checker == 61)
    {
        cout << "Yes short straight" << endl;
    }

    return 0;
}
person Hayden    schedule 06.03.2015

Я объединяю все рулоны в одну переменную.

32-битный long может легко хранить все счетчики:

//Number of ones     V
long result = 0x000000;
// sixes        ^

Каждая шестнадцатеричная цифра может содержать значение от 0 до F (15), поэтому этого достаточно для 15 бросков, а вам нужно только 5.

Ваш длинный стрит будет 0x111110 или 0x011111. Фулл-хаус 555-33 равен 0x030200. Короткий стрит немного сложнее, он выглядит как 0x101111 или 0x001121. Чтобы избавиться от этой 2, я бы использовал битовый сдвиг: long test = (result | (result>>1)) & 0x777777, а затем простую проверку: test & 0x001111 == 0x001111 и т. д.

person MSalters    schedule 06.03.2015