The question comes with calculating combos with a pair/ high card. With a pair in 5-card poker you would just calculate the odds of a pair with 3 singletons. With the possibility of 4-card hands, those 3 singletons could complete the poker hands. Here's what I have so far:
The explanation is 13 possible ranks for the pair picking out 2 of 4 suits for that pair. we pick 3 more ranks out of 12 remaining for the singletons (all standard so far) and I subtract the 44 stretches (2 given pair of 2's, 4 given a pair of 7's, etc.) over the 13 ranks. I then multiply by 4^3 for the possible suits of the singletons and subtract 2 for the cases where all 3 singletons match either paired card. I then add back the straight flush with a pair possibilities because I think I double-subtracted them?
choosing 5 singletons out of 13 ranks and subtracting the 10 5straight stretches and 78(I calculated) 4straight stretches multiplied by 4^5 for all the suits of the singletons minus 4 5flushes and 20 4flushes
4 suits times picking 4 cards out of 13 ranks - 11 straight flush stretches * 39 non-suited kickers(5 card flush would outrank) - 120 5-card straights with 4 suited cards (I calculated)
9 4straights with 2 kicker ranks that would complete a 5straight (ie. not A,2,3,4 or J,Q,K,A) times 4 suits for the 4 cards - 4 sflushes times 40 kickers that wont improve the hand added to that 2 4straights of the same thing times 44 kickers that wont improve the hand. I then subtract the 4straight hands that are also 4flush hands (again that I calculated) since flush outranks straight
right now in my sheet I'm double-counting ~7k hand combinations and can't figure out where they're coming from. numbers where "I calculated" could easily be wrong. Thanks for any help
Quote: richodudeI'm trying to calculate the hand odds of 5-card stud with 4 and 5-card poker hands. To clarify all the normal poker hands with the addition of 4-card flushes and straights. For calculation purposes, a 4-card flush outranks a 4-card straight. Each of those hands lose to a three of a kind and beat a two pair. A math check is in dire need.
The question comes with calculating combos with a pair/ high card. With a pair in 5-card poker you would just calculate the odds of a pair with 3 singletons. With the possibility of 4-card hands, those 3 singletons could complete the poker hands. Here's what I have so far:
The explanation is 13 possible ranks for the pair picking out 2 of 4 suits for that pair. we pick 3 more ranks out of 12 remaining for the singletons (all standard so far) and I subtract the 44 stretches (2 given pair of 2's, 4 given a pair of 7's, etc.) over the 13 ranks. I then multiply by 4^3 for the possible suits of the singletons and subtract 2 for the cases where all 3 singletons match either paired card. I then add back the straight flush with a pair possibilities because I think I double-subtracted them?
choosing 5 singletons out of 13 ranks and subtracting the 10 5straight stretches and 78(I calculated) 4straight stretches multiplied by 4^5 for all the suits of the singletons minus 4 5flushes and 20 4flushes
4 suits times picking 4 cards out of 13 ranks - 11 straight flush stretches * 39 non-suited kickers(5 card flush would outrank) - 120 5-card straights with 4 suited cards (I calculated)
9 4straights with 2 kicker ranks that would complete a 5straight (ie. not A,2,3,4 or J,Q,K,A) times 4 suits for the 4 cards - 4 sflushes times 40 kickers that wont improve the hand added to that 2 4straights of the same thing times 44 kickers that wont improve the hand. I then subtract the 4straight hands that are also 4flush hands (again that I calculated) since flush outranks straight
right now in my sheet I'm double-counting ~7k hand combinations and can't figure out where they're coming from. numbers where "I calculated" could easily be wrong. Thanks for any help
link to original post
Are you subtracting out the lower hands if they are also part of a higher qualifying hand?
For example, you could have both a pair and a 4 card straight or a pair and a 4 card flush. You don't want to count both of them.
Make separate categories out of 4 card straight plus a pair, 4 card flush plus a pair, and 4 card SF plus a pair.
I count 12,288 low straights A234, 135,168 straights not using the Ace as a low card, and 55,770 high flushes. Now, removing all hands that also have flushes, straights, or SFs, I get:
Hand, Pay, #Flops
Royal, 800.00, 4
Str_Flush, 50.00, 36
Quads, 25.00, 624
Full_House, 9.00, 3744
Flush, 6.00, 5108
Straight, 4.00, 10200
Trips, 3.00, 54912
Flush4, 2.70, 14376
Straight4, 2.30, 97476
Two_Pair, 2.00, 123552
JOB, 1.00, 333696
Nada, 0.00, 1955232
EDIT: I think I am double counting the low 4-straights. The totals I gave above have 11 times more straights than low straights. The straights can start with 11 ranks, so 135,168 includes all 4-straights.
Game Pay Table : 'Jacks or Better'"
Hand, Pay, #Flops
Royal, 800.00, 4
Str_Flush, 50.00, 36
Quads, 25.00, 624
Full_House, 9.00, 3744
Flush, 6.00, 5108
Straight, 4.00, 10200
Trips, 3.00, 54912
Flush4, 2.70, 15324
Straight4, 2.30, 96528
Two_Pair, 2.00, 123552
JOB, 1.00, 333696
Nada, 0.00, 1955232
My diagnostic hand listings use colors for suits on my xterm console. I should figure out how to list all the hands in color using the formatting codes here. Then I could post a list of all of the hands here.
Quote: gordonm888
Make separate categories out of 4 card straight plus a pair, 4 card flush plus a pair, and 4 card SF plus a pair.
link to original post
This bit is really helpful. I started again today with a fresh mind and think I've got it. The cells marked "(calculated)" are my answers
4sflush | 2,032 |
---|---|
4flush w/ 5straight | 360 |
4flush w/ pair | 34,320 |
4flush w/ kicker | 102,600 |
4flush (theoretical) | 134,888 |
4flush (calculated) | 134,888 |
4straight w/ 4flush | 1,320 |
4straight w/ 5straight | 10,200 |
4straight w/ pair | 33,264 |
4straight w/ kicker | 89,592 |
4straight (theoretical) | 121,536 |
4straight (calculated) | 121,536 |
4sflush | =36*46+8*47 |
---|---|
4flush w/ 5straight | =4*30*3 |
4flush w/ pair | =4*COMBIN(13,4)*12 |
4flush w/ kicker | =4*COMBIN(13,4)*36-360 |
4flush (theoretical) | =4*(COMBIN(13,4)*48) - B22-B23 |
4flush (calculated) | =sum(B24:B25) - B22 |
4straight w/ 4flush | =(11*4^4)*12/256*10 |
4straight w/ 5straight | =10*(4^5-4) |
4straight w/ pair | =11*(4^4-4)*12 |
4straight w/ kicker | =11*(4^4-4)*36-B27 |
4straight (theoretical) | =11*(4^4-4)*48-B27-B26 |
4straight (calculated) | =SUM(B28,B29)-B26 |
I used google sheets on cells A22-B33 for this with the order slightly different. I had it
4sflush (red)
4flush w/ 5straight (yellow)
4flush w/ pair (green)
4flush w/ kicker (green)
4straight w/ 4flush (red)
4straight w/ 5straight (red)
4straight w/ pair (green)
4straight w/ kicker (green)
4flush (orange)
4straight (blue)
4flush (calculated) (orange)
4straight (calculated) (blue)
where a red cell got subtracted from each respective total cell, a yellow got subtracted only from the theoretical, and green was what was added in the calculated cells. I'm sure there's a better way to display this information but I couldn't be bothered finding how.
There is a special case where a 4-card straight with a pair where the paired card also forms a 4-card flush. It happens to be that every single scenario of this forms a 4 card straight flush which I already subtracted out.
These calculations help me with the whole hierarchy
royal flush | 4 |
---|---|
straight flush | 36 |
4 card royal | 188 |
quads | 624 |
4 card straight flush | 1,844 |
full house | 3,744 |
flush | 5,108 |
straight | 10,200 |
trips | 54,912 |
4 card flush | 134,888 |
4 card straight | 121,536 |
two pair | 123,552 |
pair | 1,030,656 |
high card | 1,111,668 |
total (theoretical) | 2,598,960 |
total (calculated) | 2,598,960 |
I'm somewhat confident in these numbers but now have some decisions about the game. Should 4-card flush still outrank straight and two pair? The difference is little and would be more intuitive for people without the numbers and knowledge of 5-card hands. Next, how would I add sections for ace high/king high/queen high etc. combinations? Normally it wouldn't be so bad but the 4-card combos really screw you.
Commenting on Mental's calculations, I'm curious as to how your code got lower answers than me. The 4flush is definitely too low at only 3x more likely than a 5flush but the 4straight is ballpark. I like the video poker prediction but this will be a stud game of player vs. dealer. Hoping to get into game invention and looking at a class in LV in August where corporations can buy final projects (table game ideas).
To be clear, I am not calculating the number of 4-card hands. I am calculating the number of 4-card hands that are not contained within a higher paying hand. An 5-card flush contains 5 different 4-card flushes, right? A 5-card straight contains two different 4-card straights.Quote: richodude
Commenting on Mental's calculations, I'm curious as to how your code got lower answers than me. The 4flush is definitely too low at only 3x more likely than a 5flush but the 4straight is ballpark. I like the video poker prediction but this will be a stud game of player vs. dealer. Hoping to get into game invention and looking at a class in LV in August where corporations can buy final projects (table game ideas).
link to original post
I am calculating the 5-card stud probabilities for getting paid for a certain hand, because that is what you need for the EV. I did not look at your spoiler, but I suppose you are just getting the raw numbers without accounting for counterfeiting.
If I make the 4-straight pay more than the 5-flush and 5-straight I will get a larger number of 4-straights. I will look to see if I am catching al 4-flushes tomorrow.
Quote: MentalTo be clear, I am not calculating the number of 4-card hands. I am calculating the number of 4-card hands that are not contained within a higher paying hand. An 5-card flush contains 5 different 4-card flushes, right? A 5-card straight contains two different 4-card straights.
I am calculating the 5-card stud probabilities for getting paid for a certain hand, because that is what you need for the EV. I did not look at your spoiler, but I suppose you are just getting the raw numbers without accounting for counterfeiting.
If I make the 4-straight pay more than the 5-flush and 5-straight I will get a larger number of 4-straights.
link to original post
Sorry if any of my words seem pointless/rude, I'm just trying to be thorough
"A 5-card flush contains 5 different 4-card flushes, right?" Yes. The hand A♥2♥3♥4♥5♥ contains 1 5-card [straight] flush and 5 4-card flushes (one for every rank removed). However there should be considerably more due to the possibility of hands like A♥2♥3♥4♥5♣. Ignoring the 5straight and 4sflush, the 5th card is not a heart meaning an extra 39 kickers for a lot of extra combos. but there are also many 4flush combos where the kicker forms a 5straight which outranks and needs to be subtracted.
"A 5-card straight contains two different 4-card straights." Also yes, but a 5straight outranks a 4straight so shouldn't be counted. Your numbers seem to justify your process though, but our results are different somehow.
"If I make the 4-straight pay more than the 5-flush and 5-straight I will get a larger number of 4-straights." Yes but I don't think that difference is why our results differ. Our 4straight combos differ by almost 30k, but the 4sflush, 4flush w/ 4straight, and 5straight/sflush hands (the hands containing 4straights that have something better) don't even total 15k (according to my results) That means one or both of our calcs are wrong.
If you think any of my logic is wrong, please let me know
Hand, Pay, #Flops
Royal, 800.00, 4
Str_Flush, 50.00, 36
Quads, 25.00, 624
Full_House, 9.00, 3744
Flush, 6.00, 5108
Straight, 4.00, 10200
Trips, 3.00, 54912
Flush4, 2.70, 110940
Straight4, 2.30, 92208
Two_Pair, 2.00, 123552
JOB, 1.00, 323268
Nada, 0.00, 1874364
Quote: richodudeQuote: gordonm888
Make separate categories out of 4 card straight plus a pair, 4 card flush plus a pair, and 4 card SF plus a pair.
link to original post
This bit is really helpful. I started again today with a fresh mind and think I've got it. The cells marked "(calculated)" are my answers
4sflush 2,032 4flush w/ 5straight 360 4flush w/ pair 34,320 4flush w/ kicker 102,600 4flush (theoretical) 134,888 4flush (calculated) 134,888 4straight w/ 4flush 1,320 4straight w/ 5straight 10,200 4straight w/ pair 33,264 4straight w/ kicker 89,592 4straight (theoretical) 121,536 4straight (calculated) 121,536
4sflush =36*46+8*47 4flush w/ 5straight =4*30*3 4flush w/ pair =4*COMBIN(13,4)*12 4flush w/ kicker =4*COMBIN(13,4)*36-360 4flush (theoretical) =4*(COMBIN(13,4)*48) - B22-B23 4flush (calculated) =sum(B24:B25) - B22 4straight w/ 4flush =(11*4^4)*12/256*10 4straight w/ 5straight =10*(4^5-4) 4straight w/ pair =11*(4^4-4)*12 4straight w/ kicker =11*(4^4-4)*36-B27 4straight (theoretical) =11*(4^4-4)*48-B27-B26 4straight (calculated) =SUM(B28,B29)-B26
I used google sheets on cells A22-B33 for this with the order slightly different. I had it
4sflush (red)
4flush w/ 5straight (yellow)
4flush w/ pair (green)
4flush w/ kicker (green)
4straight w/ 4flush (red)
4straight w/ 5straight (red)
4straight w/ pair (green)
4straight w/ kicker (green)
4flush (orange)
4straight (blue)
4flush (calculated) (orange)
4straight (calculated) (blue)
where a red cell got subtracted from each respective total cell, a yellow got subtracted only from the theoretical, and green was what was added in the calculated cells. I'm sure there's a better way to display this information but I couldn't be bothered finding how.
There is a special case where a 4-card straight with a pair where the paired card also forms a 4-card flush. It happens to be that every single scenario of this forms a 4 card straight flush which I already subtracted out.
These calculations help me with the whole hierarchy
royal flush 4 straight flush 36 4 card royal 188 quads 624 4 card straight flush 1,844 full house 3,744 flush 5,108 straight 10,200 trips 54,912 4 card flush 134,888 4 card straight 121,536 two pair 123,552 pair 1,030,656 high card 1,111,668 total (theoretical) 2,598,960 total (calculated) 2,598,960
I'm somewhat confident in these numbers but now have some decisions about the game. Should 4-card flush still outrank straight and two pair? The difference is little and would be more intuitive for people without the numbers and knowledge of 5-card hands. Next, how would I add sections for ace high/king high/queen high etc. combinations? Normally it wouldn't be so bad but the 4-card combos really screw you.
Commenting on Mental's calculations, I'm curious as to how your code got lower answers than me. The 4flush is definitely too low at only 3x more likely than a 5flush but the 4straight is ballpark. I like the video poker prediction but this will be a stud game of player vs. dealer. Hoping to get into game invention and looking at a class in LV in August where corporations can buy final projects (table game ideas).
link to original post
In your categories, when you use the word kicker, you might substitute the word "singleton" when it is meant that the uncoordinated 5th card is unpaired.
I was going to cite the omission of '4 straight +4 flush + pair' as a category and thus that your '4-straight + pair' may be too high. I do now see your note on '4 straight +4 flush + pair' hands but I still wonder if '4 straight + pair' is too high because of double counting.
Okay, except for that typo that I spotted last night, I do not see any other mistakes. I assigned my 4-straights and 4-flush types a different way than the previous iteration and I still get the same results as the previous post.Quote: MentalOkay, I just looked at my code and saw a single character typo in the 4-flush code.
Hand, Pay, #Flops
Royal, 800.00, 4
Str_Flush, 50.00, 36
Quads, 25.00, 624
Full_House, 9.00, 3744
Flush, 6.00, 5108
Straight, 4.00, 10200
Trips, 3.00, 54912
Flush4, 2.70, 110940
Straight4, 2.30, 92208
Two_Pair, 2.00, 123552
JOB, 1.00, 323268
Nada, 0.00, 1874364
Just to make comparisons easier, I defined a pair as twos or better and reran the calculation:
Hand, Pay, #Flops
Royal, 800.00, 4
Str_Flush, 50.00, 36
Quads, 25.00, 624
Full_House, 9.00, 3744
Flush, 6.00, 5108
Straight, 4.00, 10200
Trips, 3.00, 54912
Flush4, 2.70, 110940
Straight4, 2.30, 92208
Two_Pair, 2.00, 123552
2OB, 1.00, 1047552
Nada, 0.00, 1150080
If I restrict my count to hands that only use J,Q,K, and A, I count 48 hands that qualify as 4-flushes and 1488 hands that qualify as 4-straights. The 48 is four suits x 12 kickers. Here are the 48 possible 4-flushes:
JQKAJ
JQKAQ
JQKAK
JQKAA
JQKAJ
JQKAQ
JQKAK
JQKAA
JQKAJ
JQKAQ
JQKAK
JQKAA
JJQKA
JJQKA
JJQKA
QJQKA
QJQKA
QJQKA
KJQKA
KJQKA
KJQKA
AJQKA
AJQKA
AJQKA
JQKAJ
JQKAQ
JQKAK
JQKAA
JQKAJ
JQKAQ
JQKAK
JQKAA
JJQKA
JJQKA
QJQKA
QJQKA
KJQKA
KJQKA
AJQKA
AJQKA
JQKAJ
JQKAQ
JQKAK
JQKAA
JJQKA
QJQKA
KJQKA
AJQKA
Hand, Pay, #Flops
Royal, 800.00, 4
Str_Flush, 50.00, 36
RF4, 40.00, 188
Quads, 25.00, 624
SF4, 15.00, 1844
Full_House, 9.00, 3744
Flush, 6.00, 4792
Straight, 4.00, 9960
Trips, 3.00, 54912
Flush4, 2.70, 109464
Straight4, 2.30, 92208
Two_Pair, 2.00, 123552
2OB, 1.00, 1047552
Nada, 0.00, 1150080
I believe your flush number is wrong. You have flush = 5,108, but that is the total number of flushes that are not SF5 and RF5. Some of the Flushes are also also RF4 and SF4, so the number of plain 5-flushes has to be less than 5,108. Am I missing something about how you are defining and counting hands? A hand can only evaluate to one type, right?
Here are the flops for the traditional JOB VP hands.
Hand, Pay, #Flops
Royal, 800.00, 4
Str_Flush, 50.00, 36
Quads, 25.00, 624
Full_House, 9.00, 3744
Flush, 6.00, 5108
Straight, 4.00, 10200
Trips, 3.00, 54912
Two_Pair, 2.00, 123552
JOB, 1.00, 337920
Nada, 0.00, 2062860
Quote: MentalI added in SF4 and RF4 hands because these eat up some of the 4-flush and 4-straight hands.
So, we agree on everything except the straights and flushes.Hand, Pay, #Flops
Royal, 800.00, 4
Str_Flush, 50.00, 36
RF4, 40.00, 188
Quads, 25.00, 624
SF4, 15.00, 1844
Full_House, 9.00, 3744
Flush, 6.00, 4792
Straight, 4.00, 9960
Trips, 3.00, 54912
Flush4, 2.70, 109464
Straight4, 2.30, 92208
Two_Pair, 2.00, 123552
2OB, 1.00, 1047552
Nada, 0.00, 1150080
I believe your flush number is wrong. You have flush = 5,108, but that is the total number of flushes that are not SF5 and RF5. Some of the Flushes are also also RF4 and SF4, so the number of plain 5-flushes has to be less than 5,108. Am I missing something about how you are defining and counting hands? A hand can only evaluate to one type, right?
Here are the flops for the traditional JOB VP hands.Hand, Pay, #Flops
Royal, 800.00, 4
Str_Flush, 50.00, 36
Quads, 25.00, 624
Full_House, 9.00, 3744
Flush, 6.00, 5108
Straight, 4.00, 10200
Trips, 3.00, 54912
Two_Pair, 2.00, 123552
JOB, 1.00, 337920
Nada, 0.00, 2062860
link to original post
My responses are usually quick. Why the delay? well I've been teaching myself to program of course! It's far from perfect, but I believe my logic for the 4-card hands is correct. Well, what did I get? Out of 2.6m random hands, ~95k of them were 4-card straights and ~89.5k were 4-card flushes. Along with ~1.16m high cards, ~1.05m pairs, ~54.8k trips and so on. Both of these 4-card hands still contain straight flush combos and I'm working that out but its 6:30 in the morning and I want to share something before I crash. That means your 4straight result is most likely correct! But how is my mathematical solution wrong? My brain already hurts and I don't wanna figure that out. That means then the actual number of 4flush combos should be closer to 86k, unless my code logic is undercounting something but it shouldn't with the lines
if temp_suit.count(0) == 4 or temp_suit.count(1) == 4 or temp_suit.count(2) == 4 or temp_suit.count(3) == 4:
is_4flush = True
where suits have a value of 0-3 hearts-spades. The hand is ranked higher than 4straight so that's not undercounted. I'd take another look at how you're counting 4flushes. I'll definitely have another go tomorrow and use this code to build onto the full game. I could provide the code somewhere if you'd like
Also, yes. That 5108 flush count is a silly mistake from me
Good for you. I don't think I could get very far with just a spreadsheet. Is this C++?Quote: richodudeMy responses are usually quick. Why the delay? well I've been teaching myself to program of course! It's far from perfect, but I believe my logic for the 4-card hands is correct. Well, what did I get? Out of 2.6m random hands, ~95k of them were 4-card straights and ~89.5k were 4-card flushes. Along with ~1.16m high cards, ~1.05m pairs, ~54.8k trips and so on. Both of these 4-card hands still contain straight flush combos and I'm working that out but its 6:30 in the morning and I want to share something before I crash. That means your 4straight result is most likely correct! But how is my mathematical solution wrong? My brain already hurts and I don't wanna figure that out. That means then the actual number of 4flush combos should be closer to 86k, unless my code logic is undercounting something but it shouldn't with the lines
if temp_suit.count(0) == 4 or temp_suit.count(1) == 4 or temp_suit.count(2) == 4 or temp_suit.count(3) == 4:
is_4flush = True
where suits have a value of 0-3 hearts-spades. The hand is ranked higher than 4straight so that's not undercounted. I'd take another look at how you're counting 4flushes. I'll definitely have another go tomorrow and use this code to build onto the full game. I could provide the code somewhere if you'd like
Also, yes. That 5108 flush count is a silly mistake from me
link to original post
I learned 25 years ago that the double counting problem is hard and prone to subtle errors. I wanted a general solution. What I do to handle double counting is to write a series of functions defining any hand type in terms of five indices i0, i1, i2, i3, i4 which range from 0-51 for a standard deck with no jokers. Nada is the type that you refer to as 'high card'. In my VP program, I could assign a payoff to Nada if I wanted to. When my program reads in a pay table, it sets a variable is'Type' to the line number in the pay table (where 'Type' is a specific hand type like Flush). Every specific variable isType is initialized to -1 before this. The first thing any of these hand-definition functions does is check the type. If it is less than 0, then that particular type was never defined in the pay table and I can skip it.
void handInfo::setNada(int type)
{
int k, int i0, i1, i2, i3, i4;
if (type < 0) return; // isNada type was not found in pay table
for (i0 = 0; i0 < 48; i0++) {
for (i1 = i0 + 1; i1 < 49; i1++) {
for (i2 = i1 + 1; i2 < 50; i2++) {
for (i3 = i2 + 1; i3 < 51; i3++) {
for (i4 = i3 + 1; i4 < 52; i4++) {
k = indexHand(i0, i1, i2, i3, i4);
tentative(k, type);
}
}
}
}
}
}
All I did to implment you stud game was to add three new hand-definition functions and call them like this:
setSF4(v.isSF4, v.isRF4); // 4-Flush
setFl4(v.isFlush4); // 4-Flush
setStr4(v.isStr4); // 4-Straight
Here. v.isStr4 is the new type of a 4-Straight, etc. The setSF4() function defines 4-SF and 4-RF hands in the same function. A single hand could be resolved to isNada, isStr4, isFlush4, isStraight, isFlush, isSF4, isSF, and isRF. Only the last type would stick. Other hands could resolve to isNada, isHiPair, isStr4, isFlush4.
The indexHand(i0, i1, i2, i3, i4) function is implemented as an array lookup table. It is generic and reusable for any game. I currently support single and double joker games, so I can quickly index 54 choose 5 = 3162510 different hands. You could use a hash table to do this indexing faster, but the hash table would consume a lot of memory.
Quote: MentalIs this C++?
Python. Learned a tiny bit, made switching to other languages harder so stuck with it. I can still run ~150k hands/second on a r5 3600.
Anyways, I'm here to share my refined code update. I can confirm our results now match exactly. Hooray! Some things that were wrong were: the super simple checking for suits 0-3 when the suits were labeled 1-4 ;-; also I added 4sflush checks which was by far the most difficult thing with my logic. There was also this weird bug in my logic where the hand [A,K,4,3,2] would not register as a straight but [A,x,4,3,2] would.
You can check out my project at https://github.com/richodude/MinnesotaStud/tree/master
The part I'm most proud of is the logic I used to rank hands. Looking online, there's surprisingly little (at least that I understood) about programming poker. I took a concept from someone who categorized poker hand in excel and it will likely work with many cards and any poker combo.
Start by taking your list [x,x,x,x,x] and arrange your cards in order. I also had my cards in number form pulling from the list 2♥,2♣,2♦,2♠,3♥...A♠. So the hand [0,1,2,3,51] would be 2♥,2♣,2♦,2♠,A♠
Then do whatever you need to have the rank and suit separate. For example in the above list I made two separate lists, [2,2,2,2,14] and [1,2,3,4,4]. I'll call them the 'rank_list' and 'suit_list'
To find pairs, sets, two pairs, quads, and full houses, we can make another list I'll call 'has_pair'. Start by comparing index 0 and 1 (first and second number) and if they're the same, add 1 to the has_pair list, and if not, a 0. continue until index 4,5 where we will have a list looking like [1,1,1,0] Another example for [3♣,5♦,5♠,K♥,K♦] would yield the list [0,1,0,1]. The has_pair list determines the hand rank. [1,0,0,0] [0,1,0,0] [0,0,1,0] or [0,0,0,1] is just a pair, [1,0,1,0] [1,0,0,1] or [0,1,0,1] is two pair, [1,1,0,0] [0,1,1,0] or [0,0,1,1] is trips, [1,1,0,1] or [1,0,1,1] is a full house, and [1,1,1,0] or [0,1,1,1] is quads. A lot to read but the pattern is there.
to find flushes, you just find the mode of suit_list and if it's at least 4, you have a 4-card flush or better
to find straights (the tricky part) is actually pretty easy. I make another list called 'connector_list' and use it similarly to pair_list. if index 1 minus index 0 = 1, those two cards are connected to form a potential straight. the list [1,1,1,1] means a 5-card straight. Ace is 14 in my code so I added special logic for the case where the list is [1,1,1,0] and there is an Ace-Two present. 4-cards is a bit trickier but not too bad. lists [1,1,1,0] and [0,1,1,1] are 4straights, but also any single pair hand where the connector_list XOR the pair_list is [1,1,1,1] For example if the hand is [3♣,4♠,5♠,5♥,6♦] our connector_list would be [1,1,0,1] and the pair_list would be [0,0,1,0] XOR'ing combines the lists where they are not matching.
4-card straight flushes were pretty scuffed with the sheer amount of edge cases. Look at lines ~140 in HandRanking.py if you want to see how I did it
Most of this code was my brain doing the work, but every programmer knows there's some BS line that you need that you would never figure out yourself so thanks chatGPT for that. It also taught me a dual-line solution for cycling through all ~2.6 million hand combinations
import itertools
combinations = itertools.combinations(range(0,52),5)
for hand in combinations:
rank_the_hand()
remember python is line based rather than bracket/semicolon/whatever-else-you-use based in case it looks weird
Now I can actually move on to the game... *sudden realisation I've barely started this project*
I use python where I have to, but I am not proficient. I can usually understand code in any procedural programming language.
When I started out, I used an approach similar to the one you describe. But, I like to code fast and then check for mistakes. Someone who is more methodical than me might be able to code these classifying functions better than I can. I found that I make less mistakes by defining every hand within a class, and then having the program sort out which one is ranked highest. I can have my program print out any subset of hands with color coding for suits. I usually can spot any errors quickly.
The Wizard has a page somewhere on indexing any hand to an integer quickly. When I dug into the algorithm, it is equivalent to my array lookup table. That is, his indexing formula is equivalent to the math that the processor does to calculate the address of an element in a 4-dimensional array like the one I use. Since compiler know how to do array-index math very efficiently, my method is just a bit faster, but both methods are very fast in C++.
Let me know if you want or need any help with fast hand indexing. Since you are working on a stud game, you won't need fast code for drawing cards. If I recall correctly, I got hints for using the Serpinski triangle for this task from VP Genius. This is really the only way to go.