Ranges de posição para bots de pôquer: pare de abrir de qualquer lugar
Seu bot de pôquer não deve jogar as mesmas mãos em todas as posições. No No-Limit Hold'em 6-max, o botão age por último depois do flop, enquanto os blinds agem primeiro. Essa diferença determina quais mãos geram fichas e quais drenam o stack silenciosamente.
Parte de: O guia completo para construir um bot de IA para poker em 2026 - o pilar completo que cobre estruturas, lógica de decisão, equidade, testes e onde competir.
Principais conclusões
- Os ranges de posição são uma vantagem barata porque corrigem erros pré-flop antes que a mão fique cara.
- As posições iniciais exigem ranges tight. Nas posições finais, é possível tentar roubos com mais frequência porque restam menos jogadores para agir.
- Primeiro, implemente os ranges como conjuntos de códigos de mãos. Adicione a modelagem de oponentes somente depois que essa base funcionar.
Por que a posição importa tanto
A posição é importante porque quem age mais tarde toma decisões com mais informação. A documentação de estratégia do Open Poker destaca posição inicial, posição final e blinds como contextos de decisão distintos (documentos de ações e estratégia). Num jogo 6-max, cada órbita tem seis posições e 30 fichas obrigatórias em blinds na estrutura 10/20.
Ao abrir KTo under the gun, o bot ainda enfrenta cinco jogadores. Ao abrir a mesma mão no botão, restam apenas os dois blinds. As cartas são as mesmas; o risco não.
É nesse ponto que bots iniciantes perdem fichas sem perceber. Eles calculam um único valor em hand_strength() e o usam em todas as posições. Isso funciona com mãos óbvias, como um par de ases, mas falha justamente nas mãos que decidem boa parte de uma temporada: suited connectors, ases fracos, pares baixos e broadways marginais.
Quais são as seis posições úteis
Use seis posições: UTG, HJ, CO, BTN, SB e BB. Open Poker envia dealer_seat em hand_start; o bot recebe o próprio assento em table_joined e pode calcular a posição relativa a partir desses dois valores (documentação do WebSocket).
POSITIONS_6MAX = ["SB", "BB", "UTG", "HJ", "CO", "BTN"]
def position_name(hero_seat, dealer_seat, active_seats):
ordered = sorted(active_seats)
dealer_index = ordered.index(dealer_seat)
relative = ordered[(dealer_index + 1) % len(ordered):] + ordered[:dealer_index + 1]
# relative[0] is small blind, relative[1] is big blind in a full hand.
seat_to_position = {
seat: POSITIONS_6MAX[i]
for i, seat in enumerate(relative[: len(POSITIONS_6MAX)])
}
return seat_to_position[hero_seat]Uma mesa pode não estar completa. Se houver apenas três bots, use somente a lógica de BTN, SB e BB. Não trate um assento como under the gun quando só existem três jogadores ativos.
Quais ranges de abertura um primeiro bot deve usar
Comece com ranges mais tight do que você imagina. Uma base prática para iniciantes é abrir 12% no UTG, 16% no HJ, 22% no CO, 35% no BTN e usar um range cauteloso no small blind. Esses números não vêm de um solver perfeito, mas evitam os piores vazamentos enquanto você aprimora a lógica pós-flop.
| Posição | Alvo aberto | Mãos de exemplo |
|---|---|---|
| UTG | 12% | 77+, AJs+, KQs, AQo+ |
| HJ | 16% | 66+, ATs+, KJs+, QJs, AJo+ |
| CO | 22% | 55+, A8s+, KTs+, QTs+, JTs, ATo+, KQo |
| BTN | 35% | 22+, mais ases suited, broadways e suited connectors |
| SB | 28% | Dê raise com mãos que jogam bem em heads-up e folde as piores |
| BB | Defender conforme o preço | Dê call com base nas pot odds e na jogabilidade da mão |
As porcentagens exatas importam menos do que o formato geral: tight no início, amplo no botão e ajustado com cuidado nos blinds. Essa estrutura corrige mais bots iniciantes do que outra heurística pós-flop.
Para considerar a profundidade do stack, combine esses ranges com o gerenciamento de stack para bots de pôquer. Um bot com 50bb e outro com 250bb não devem tratar pares baixos da mesma forma.
Como você codifica ranges em Python
Codifique as mãos com strings curtas: AA, AKs, AQo. Pares repetem o valor. Mãos suited terminam em s; mãos offsuit, em o. O formato é compacto para ranges escritos à mão e fácil de depurar nos logs.
RANK_ORDER = "23456789TJQKA"
def hand_code(cards):
r1, s1 = cards[0][0], cards[0][1]
r2, s2 = cards[1][0], cards[1][1]
if r1 == r2:
return r1 + r2
high, low = sorted([r1, r2], key=RANK_ORDER.index, reverse=True)
suited = "s" if s1 == s2 else "o"
return high + low + suited
OPEN_RANGES = {
"UTG": {"77", "88", "99", "TT", "JJ", "QQ", "KK", "AA", "AJs", "AQs", "AKs", "KQs", "AQo", "AKo"},
"HJ": {"66", "77", "88", "99", "TT", "JJ", "QQ", "KK", "AA", "ATs", "AJs", "AQs", "AKs", "KJs", "KQs", "QJs", "AJo", "AQo", "AKo"},
"CO": {"55", "66", "77", "88", "99", "TT", "JJ", "QQ", "KK", "AA", "A8s", "A9s", "ATs", "AJs", "AQs", "AKs", "KTs", "KJs", "KQs", "QTs", "QJs", "JTs", "ATo", "AJo", "AQo", "AKo", "KQo"},
"BTN": {"22", "33", "44", "55", "66", "77", "88", "99", "TT", "JJ", "QQ", "KK", "AA", "A2s", "A3s", "A4s", "A5s", "A6s", "A7s", "A8s", "A9s", "ATs", "AJs", "AQs", "AKs", "K9s", "KTs", "KJs", "KQs", "Q9s", "QTs", "QJs", "J9s", "JTs", "T9s", "98s", "87s", "A9o", "ATo", "AJo", "AQo", "AKo", "KTo", "KJo", "KQo", "QJo"},
}
def should_open(position, cards):
return hand_code(cards) in OPEN_RANGES.get(position, set())É uma implementação simples de propósito. Quando o bot acumular uma sequência de folds, você poderá registrar position=CO hand=KTo open=False e entender a decisão imediatamente.
Como você usa ranges com ações válidas
Abra o pote somente quando ninguém tiver apostado e o raise for uma ação válida. Open Poker informa todas as ações permitidas, inclusive os valores mínimo e máximo de raise. O valor representa o total do raise, não o incremento, uma confusão comum em bots (documentação de ações).
def preflop_decision(msg, hole_cards, position):
actions = {a["action"]: a for a in msg["valid_actions"]}
# Free option in the big blind.
if "check" in actions:
return "check", None
if "raise" in actions and should_open(position, hole_cards):
return "raise", actions["raise"]["min"]
# Facing a raise: use a tighter continue range for now.
if "call" in actions and hand_code(hole_cards) in {"TT", "JJ", "QQ", "KK", "AA", "AQs", "AKs", "AKo"}:
return "call", None
return "fold", NoneEsse range de call é intencionalmente tight. Dar call com mãos demais é uma das formas mais rápidas de transformar um bot pré-flop razoável em um bot perdedor no pós-flop. Depois de implementar a equidade por Monte Carlo, amplie os calls conforme o preço e as tendências do oponente.
Quando os ranges devem mudar
Os ranges devem acompanhar mudanças na profundidade do stack, no tamanho da mesa e no perfil dos oponentes. No Open Poker, os buy-ins variam de 1.000 a 5.000 fichas, enquanto cada temporada começa com 5.000 fichas e blinds fixos de 10/20 (documentação da temporada). Assim, o mesmo bot pode jogar com 50bb, 100bb ou 250bb.
Use três ajustes:
| Contexto | Ajuste |
|---|---|
| Short stack abaixo de 60bb | Remova conectores especulativos do mesmo naipe e pares pequenos |
| Stack profundo acima de 150bb | Adicione conectores e pares do mesmo naipe na posição final |
| Blinds loose | Reduza os roubos e aposte mais por valor |
| Blinds tight | Amplie os ranges de abertura no botão e no cutoff |
Não aplique os quatro ajustes no primeiro dia. Primeiro, confirme que o range-base supera a antiga estratégia baseada em uma única pontuação. Depois, use a modelagem de oponentes para ajustar o botão e os blinds.
Como você testa um novo range
Teste os ranges com uma alteração por vez. Mudanças pré-flop parecem pequenas, mas afetam todas as streets seguintes porque o bot chega ao flop com outra composição de mãos. Se você ampliar o range do botão, soltar a defesa do big blind e mudar o sizing ao mesmo tempo, não saberá qual alteração ajudou.
Use este loop de teste:
- Escolha uma posição, geralmente BTN ou BB.
- Mude de 5 a 10 mãos nesse range.
- Execute pelo menos 300 mãos.
- Compare tendências de fichas, recompras e grandes mãos perdedoras.
- Mantenha a alteração somente se o log explicar o resultado.
O sinal mais rápido não é a taxa de vitória, mas o conjunto de mãos que entraram no pré-flop e perderam mais de 20bb. Analise essas mãos primeiro. Se o novo range do botão acrescentar cinco mãos offsuit marginais que continuam perdendo potes grandes, reverta a mudança. Se elas roubarem blinds e raramente chegarem ao showdown, continue testando.
Os resultados recompensam uma disciplina que pode parecer monótona. Bons bots não precisam de criatividade heroica pré-flop. Precisam jogar menos mãos dominadas nas posições iniciais e aplicar mais pressão controlada nas posições finais.
Perguntas frequentes
Um bot de pôquer deve usar ranges perfeitos de solver
No início, não. Ranges de solver pressupõem uma árvore de jogo específica e determinadas respostas dos oponentes. Uma tabela simples para 6-max é mais fácil de testar e registrar, além de ser melhor do que copiar um chart que o bot não sabe jogar no pós-flop.
Como o big blind defende
O big blind deve defender pelo preço. Se pagar 20 em um pote de 90 fichas, você precisará de muito menos equidade do que se pagar 200 em 300. Comece com pot odds e depois filtre as mãos que jogam mal no pós-flop.
Qual range devo usar para um bot sem código
Comece com o modelo The Shark. A documentação do Bot Builder o descreve como tight-aggressive, com 0,30 de tightness e 0,75 de agressividade, uma base mais sólida do que modelos loose para a maioria dos iniciantes.
Os ranges de posição podem substituir a avaliação das mãos
Não. Os ranges decidem se o bot entra na mão pré-flop. A avaliação da mão e a equidade orientam o que fazer depois que o board aparece. Use os dois recursos.