MahjongRepository/mahjong

[Bug] `ValueError: negative shift count` at calculating hand.(Test code included)

marko1616 opened this issue · 1 comments

Description:

I encountered a potential issue with the tile reduction logic used in the hand calculation process. The current implementation seems to decrement the tile count incorrectly, which might lead to a ValueError. I've provided a test code snippet and a link to the relevant code section for your review.

Test Code:

from mahjong.meld import Meld
from mahjong.tile import TilesConverter
from mahjong.hand_calculating.hand import HandCalculator

# Setup melds and tiles
melds = [
    Meld(meld_type=Meld.CHI, tiles=TilesConverter.string_to_136_array(sou="678")),
    Meld(meld_type=Meld.CHI, tiles=TilesConverter.string_to_136_array(man="345")),
    Meld(meld_type=Meld.CHI, tiles=TilesConverter.string_to_136_array(pin="345")),
    Meld(meld_type=Meld.PON, tiles=TilesConverter.string_to_136_array(honors="222"))
]
tiles = TilesConverter.string_to_136_array(sou='33')
win_tile = TilesConverter.string_to_136_array(sou='3')[0]

# Calculate hand value
calculator = HandCalculator()
result = calculator.estimate_hand_value(tiles=tiles, melds=melds, win_tile=win_tile)

Suspected Issue:
I suspect there might be an issue with the tiles[x] -= x logic in the code, as it seems leading to << a negative number.

Relevant Code Section:

mahjong/mahjong/agari.py

Lines 17 to 41 in cb749aa

if open_sets_34:
isolated_tiles = find_isolated_tile_indices(tiles)
for meld in open_sets_34:
if not isolated_tiles:
break
isolated_tile = isolated_tiles.pop()
tiles[meld[0]] -= 1
tiles[meld[1]] -= 1
tiles[meld[2]] -= 1
# kan
if len(meld) > 3:
tiles[meld[3]] -= 1
tiles[isolated_tile] = 3
j = (
(1 << tiles[27])
| (1 << tiles[28])
| (1 << tiles[29])
| (1 << tiles[30])
| (1 << tiles[31])
| (1 << tiles[32])
| (1 << tiles[33])
)

Expected vs. Actual Results:
For reference, here's the result from Tenhou:
Tenhou result

BTW I dont find any test case for this in this repo.