《21点》游戏规则和玩法
18:27:20 本文行家:
扑克牌 庄家在取得17点之前必须要牌,因规则不同会有软17点或硬17点才停牌的具体区分。 每位玩家的目的是要取得最接近21点数的牌来击败庄家,但同时要避免爆牌。要注意的是,若玩家爆牌在先即为输,就算随后庄家爆牌也是如此。若玩家和庄家拥有同样点数,这样的状态称为“push”,玩家和庄家皆不算输赢。每位玩者和庄家之间的游戏都是独立的,因此在同一局内,庄家有可能会输给某些玩家,但也同时击败另一些玩家。 牌桌上通常会印有最小和最大的赌注,每一间赌场的每一张牌桌的限额都可能不同。在第一笔筹码下注后,庄家开始发牌,若是从一副或两副牌中发牌,称为“pitch”牌局;较常见的则是从四副牌中发牌。庄家会发给每位玩家和自己两张牌,庄家的两张牌中会有一张是点数朝上的“明牌”,所有玩家皆可看见,另一张则是点数朝下的“暗牌”。若是四副牌时,发牌时点数会朝上,若为“pitch”牌局则发牌时点数朝下。 在美式的二十一点游戏中,若庄家的明牌是A或价值10的牌,庄家会确认他的暗牌是否会形成二十一点。这项确认会在所有玩家选择之前进行,但进行前会先询问玩家是否需要“保险”(insurance,在明牌是 A 的情况下)。若庄家的牌为二十一点(blackjack),则所有的玩家即时算输,将损失第一笔赌注筹码,除非玩者本身也是二十一点,或形成同点数的 push 状况。(在某些美国的赌场,庄家采用欧式的规则,在全部玩家都出手前不会先去确认暗牌。在这样的情况下,当庄家的牌揭开后为 二十一点时,则所有没有二十一点的玩家算输。) 两张牌点数相加为21(一张A再加一张价值10点的牌)称为“二十一点”(black jack),拥有这副牌的玩家即自动成为赢家(除非庄家也同时持有二十一点,这种点数相同的情形就称为 push)。拥有二十一点的玩家可赢得下注筹码的1.5倍。部份的赌场仅付给1.2倍的金额;但通常是在仅使用一副牌游玩的赌局中。 通常每次以四至六副扑克牌游玩,直至玩剩一副或一半为止,再重新洗牌。
参考资料:
[1] 扑克牌
百科的文章(含所附图片)系由网友上传,如果涉嫌侵权,请与***联系,我们将按照法律之相关规定及时进行处理。如需转载,请注明来源于。
我是互动百科的老用户了联众游戏->游戏介绍
――游戏起源、历史、简介
21点为一款极具趣味性的牌类游戏,最早出现在十六世纪,起源于法国,法语称:vingt-et-un
(20 和 1), 因此在广为流行后该游戏就叫“21”。后传入英国并广泛流传,如果玩家拿到 黑心“A”和
黑心“J”, 就会给与额外的奖励,英文的名字叫黑杰克(Blackjack)。
在游戏中,每个玩家都争取拿到最接近21点的牌,但是不能超过21点,超过为“爆牌”即失败,只有最接近21点的人才有可能得到胜利。
――下载和***
联众用户可以通过以下的地址来下载21点游戏
――进入游戏
首先联入Internet后,进入“联众世界大厅”选择牌类游戏中的“21点”,登录后进入游戏室,然后可自由选择对手,坐下后并选择“开始”就可以开始打牌。也可以在其他牌桌观看,只要用鼠标单击正在打牌中的人物图像即可。
――游戏描述
游戏开始先由庄家的顺时针下一家开始发牌,闲家每人两张明牌,庄家第一张明牌,第二张暗牌。闲家分别与庄家对抗。发牌后,闲家先要牌力争使自己接近21点且不“爆牌”,即“不超过21点”,闲家选择完毕后,轮到庄家按照规则要牌,庄家结束选择后按照双方的牌点是否接近21点判断输赢。
――详细规则、胜负判定方法
游戏人数 2-5人
游戏使用一副扑克牌,去掉大小王,共52张牌。
庄家:坐庄的玩家,对手为所有闲家。
闲家:除坐庄以外的玩牌者,对手为庄家。
要牌:再要一张牌。
停牌:不再要牌。
BJ:起手牌为A+(10 或 J 或 Q 或 K)=黑杰克
推:筹码退回,不收取任何费用
分牌:每手所获得第1,2张牌面数值若相同,可以分成2手牌,新分的牌筹码与另一手相同。
加倍:获得2张牌后,选择仅要一张牌后停牌,回报加倍。
各牌对应分值
2-9:牌面数值与分值相同
10、J、Q、K:均为10分值
A:可为1或者11分值,当计算11分值时会爆牌,则自动记为1分值。
确定庄家:首次随机抽选庄家,以后顺时针轮庄。
发牌规则:由庄家的顺时针下一家开始发牌,每人两张,庄家第一张明牌,第二张暗牌。
要牌规则:闲家选择“要牌”,系统会发一张牌,到手中。
停牌规则:选择停牌后,不能再做任何操作,以当前牌面点数等待与庄家进行比较。
加倍规则:在发了起始2张牌后可以选择加倍,加倍后系统自动发一张牌随即停牌,筹码加倍。若进行了“要牌”、“停牌”、“分牌”操作后,则不能选择加倍。
分牌规则:起始牌两张相同,则可分牌,分牌后两张牌各自为一手牌,并自动收到一张新牌,筹码每手相同。
庄家规则:17点以下必须要牌,17点以上必须停牌。有A情况下可以选择要牌或者停牌。
自动停牌:庄家要牌超过17点自动停牌,庄家/闲家牌点为21自动停牌。
玩家下注时,断线超过30秒认为玩家托管。
下注时玩家超时,系统自动投入最小注。
闲家要牌超时:当牌小于等于“11”点时自动抓下一张牌,“大于“11”则不抓牌,自动停牌。
庄家要牌超时:当牌小于17点时自动抓,大于等于17点必须停牌。
闲家断线托管:当牌小于等于“11”点时自动抓下一张牌,“大于“11”则不抓牌。
庄家断线托管:当牌小于17点时自动抓,大于等于17点必须停牌。
游戏结束时,若有玩家处于托管状态,则系统自动解散游戏。若所有玩家都在托管状态,则该局游戏不予计分。
闲家爆牌则立刻判输,庄家爆牌则未爆牌的闲家均为赢家。
闲家、庄家均停牌后,闲家的每手没爆的牌与庄家牌进行比较。
BJ,即起始两张牌为“黑杰克”最大。
黑杰克&21点&其他点数。
庄家与闲家点数相同,则记为推,双方平局。
游戏的得分值与游戏中财富值的得失相同,即桌面上赢1000财富值,得分相应为+1000分;桌面上输1000财富值,得分相应为-1000分。
――21点游戏升级记录纸牌游戏21点(Blackjack).构造并实施21点游戏的蒙特卡洛模拟
纸牌游戏21点(Blackjack).构造并实施21点游戏的蒙特卡洛模拟
作者:23KL、wxj
班级:10网络ATA2班、10网络2班
本文主要讲述了如何构造纸牌游戏21点,以及如何编写编程实施21点游戏的蒙特卡洛模拟。根据现实生活中的21点游戏,可以把21点游戏的蒙特卡洛模拟的核心分成洗牌。选择牌A的点数,发牌,计算得分四个部分,采用编程中的面向对象思想,用Java语言编写一个游戏类,四个成员方法以实现蒙特卡洛模拟。
[问题重述]:
纸牌游戏21点(Blackjack).是世界各地赌场里最受欢迎的牌桌游戏之一,大多数赌场使用6副牌或8副牌玩这种游戏,以防止“数牌点”。为了方便模拟,在模拟中只使用两副牌共104张牌(除去大鬼和小鬼)。并且只有2位参与者,我和庄家。
我和庄家对赌,游戏的目的就是要拿到好过庄家牌的同时不超过21点。每张牌都有自己的点数,把牌的点数加在一起就得到了这一手的点数。
104张牌中分别有8个A,2,3,4,5,6,7,8,9,10,J,Q,k。其中花面牌(国王/King,王后/Queen,和杰克/Jack)的是10点,A是1点或者11点(我可以自己选择A是1点或11点,而庄家拿到A时A必须为11点,除非当A为11点时庄家的牌会爆----即庄家的点数大于21点),所有其它的牌(2-10)的点数和牌面点数相同。
21点的玩法:
& 当下注后,我和庄家都会收到2张牌。
& 庄家会显示其中一张牌,其它的牌则会正面朝下直到游戏结束。
轮到我行动时,我可以选择叫牌(次数不限,一次一张)或打住,当点数大于21点时称为爆点,我就输了。
在我完成这手牌的行动后,庄家就开始行动----若庄家牌的点数小于或等于16,必然取牌。当庄家牌的点数大于16时,就打住。庄家总把A的点数记为11,除非这样使他或她爆了(这时A的点数记为1)。
如果我在最开始得到的2张牌上得到21点(A&10),那么我可以赢取我所下赌金的1.5倍。
& 如果我和庄家同时都得到21点,那么这手牌为平局。
如果你这手牌的点数超过21点,那么我就爆点,庄家会赢得注金和不显示他的牌。
用两幅牌做12次游戏,每局赢了+2分,输了-2分,当开局得到21点并且赢了时+3分,平局+0分,每次游戏得到一个分数:-2分,0分,2分或3分;将12次比赛的成绩相加得到总成绩。输出每次游戏成绩和总成绩。
模拟中采用自己的策略进行游戏,写出模拟算法的说明书,编写程序并运行,输出12次游戏的结果并加以分析。
[问题的分析和算法设计]:
首先,21点纸牌游戏源于生活中,所以编程的实现必须从生活中的21点纸牌游戏入手。我们都知道,纸牌游戏都有洗牌,计算牌的点数,发牌,判断输赢的工序,因此21游戏的蒙特卡洛模拟可以分成大致分成四个部分:洗牌,选择牌A的点数,发牌,计算每局得分和总得分。
算法设计:
张牌组成一个数组poker[];
2)模拟洗牌工序
函数产生随机数用于洗牌。newPoker[]承接洗完的牌。
洗牌的工序是这样的:让pokerTemp []=poker
[],首先产生0-103共104个随机数(设产生的随机数为s),每次从数组pokerTemp []中取出1张牌pokerTemp
[s]放在newPoker[]中第i个位置(i初始为0)。每取出一张牌,产生的随机数s自动减去1个,即当抽取第k张扑克牌时,随机数总数为(104-k),产生的随机数为0到(103-k)。每抽取1张牌,pokerTemp
[]中牌就少1张,因此必须重新编排数组,当抽取的牌为pokerTemp [s]时,让s位置后的数前进1位,形成新的pokerTemp
[]。当抽取完104张牌都放入newPoker[]时,便完成了洗牌工序,此时newPoker[]按顺序排列了104张无序的扑克牌。发牌时,只要从newPoker[]中第1位开始取牌即可。
3)模拟选择牌A为1点或11点的工序
让牌A的初始点数为11,每次我(庄家)得到1张新牌时,计算我的(庄家的)原始总点数firstMyPoint(firstItPoint),即按牌A的点数为11计算后得到的总点数。若此时我(庄家)的牌中有myPoint_11(itPoint_11)张A,则我的总点数(庄家的总点数)范围为:firstMyPoint-myPoint_11*10到firstMyPoint(firstItPoint-itPoint_11*10到firstItPoint)。判断总点数是否大于21点,若是,则减去不大于A的张数个10,直到总点数小于或等于21点。把每次得到的最后总点数赋予endMyPoint(endItPoint),endMyPoint(endItPoint)即为最终总点数,让它参与接下来的发牌工序。
4)模拟发牌工序
发牌顺序为每次每人一张(可以是我先得到第一张牌),起初每人得到两张牌,然后每个人轮流行动(行动可以选择继续加牌或打住),当轮到我(庄家)行动时,先判断我的点数(庄家的点数)是否小于17点(我的策略和庄家一样),若是则继续加牌,直到两人都不加牌,这局游戏就此结束,接着计算输赢。
5)模拟计算得分工序
写一个算法计算得分,即:当我的点数大于21点时我就输了,-2分;否则,当庄家大于21点时,我赢了,+2分;否则,当我的点数等于庄家的点数时,游戏平局,+0分;否则,当我起初得到2张牌时点数为21时,我赢了,+3分;否则,当我的点数大于庄家的点数时,我赢了,+2分;否则,当我的点数小于庄家的点数时,我输了,-2分。
6)进行12次游戏,得到总成绩
进行12次游戏,可以让游戏循环12次,得到12次游戏得分fract,把每次的得分加起来得到总得分sumFract。就此,蒙特卡洛模拟结束。
[计算机程序设计]:
import java.util.R
public class Blackjack {
public static void main(String[] args)
int poker[]={
11,11,11,11,11,11,11,11,
2,2,2,2,2,2,2,2,
3,3,3,3,3,3,3,3,
4,4,4,4,4,4,4,4,
5,5,5,5,5,5,5,5,
6,6,6,6,6,6,6,6,
7,7,7,7,7,7,7,7,
8,8,8,8,8,8,8,8,
9,9,9,9,9,9,9,9,
10,10,10,10,10,10,10,10,
10,10,10,10,10,10,10,10,
10,10,10,10,10,10,10,10,
10,10,10,10,10,10,10,10,
sumFract=0;&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&//总得分
i=0;i&12;i++){
Game game=new
Game(poker);&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&//游戏开始
game.shuffleCard();&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&//洗牌
game.DeliverCard();&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&//发牌
System.out.println(game.fraction()+";");&&&&&&&&&&&&&&&//输出每盘得分
sumFract+=game.fraction();&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&//累计得分
System.out.println("sumFract="+sumFract);&&&&&&&&&&&&&&&//输出总分
class Game
poker[];&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&//扑克牌组
newPoker[];&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&//洗牌后的扑克牌组
&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&//分发第i张扑克牌,i=number+1
&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&//每局得分
firstMyP&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&//我的原始点数,即牌A的点数为固定值11
firstItP&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&//庄家原始点数,即牌A的点数为固定值11
endMyP&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&//我的点数,牌A根据情况确定点数为1或11
endItP&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&//庄家点数,牌A根据情况确定点数为1或11
myPoint_11;&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&//我抽到A的张数
itPoint_11;&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&//庄家抽到A的张数
public Game(int poker[]){
this.poker=&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&//传入新扑克牌,扑克牌数组为固定数组,不能改变
public void shuffleCard(){
s;&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&//随机数,初始值为0
newPoker=new
int[104];&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&//洗牌后的扑克牌
int[] pokerTemp=new
int[104];&&&&&&&&&&&&&&&&&&&&&&&&&&&//跑龙套的,作为过渡值
i=0;i&poker.i++){
pokerTemp[i]=poker[i];
i=0;i&104;i++){
Random().nextInt(104-i);&&&//产生0-104-i的随机数,当抽走1张牌时,产生的随机数自动减去1个
newPoker[i]=pokerTemp[s];
j=0;j&pokerTemp.length-i-s-1;j++){
pokerTemp[s+j]=pokerTemp[s+j+1];
public void rewrite_A(){
endMyPoint=firstMyP&&&&&&&&&&&&&&&&&&&&&&&&&&&//endMyPoint初始化成firstMyPoint
endItPoint=firstItP&&&&&&&&&&&&&&&&&&&&&&&&&&&//endItPoint初始化成firstItPoint
if(endMyPoint&21){
i=0;i&myPoint_11;i++){&&&&&&&&&&&&&&&&&&&&&//根据myPoint_11的值判断循环次数
if(endMyPoint&=21){}
endMyPoint+=-10;&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&//每次循环走到这里就有1张牌面为A点数变为1点
if(endItPoint&21){
i=0;i&itPoint_11;i++){
if(endItPoint&=21){}
endItPoint+=-10;
public void DeliverCard(){
i=1;i&0;i++){
if(endMyPoint&17){
endMyPoint+=newPoker[number];
firstMyPoint+=newPoker[number];
if(newPoker[number]==11){myPoint_11+=1;}//判断抽取的牌是否为A
System.out.print("me="+(number+1)+";"+newPoker[number]+",");
this.rewrite_A();&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&//调用方法,选择A为1点或11点
if(endMyPoint&21){}&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&
&//当我的点数大于21时跳出循环
if(endItPoint&17){
endItPoint+=newPoker[number];
firstItPoint+=newPoker[number];
if(newPoker[number]==11){itPoint_11+=1;}//判断抽取的牌是否为A
System.out.print("it="+(number+1)+";"+newPoker[number]+",");
this.rewrite_A();&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&
&//调用方法,选择A为1点或11点
if(endItPoint&21){}&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&
& //当庄家的点数大于21时跳出循环
if(endMyPoint&=17&&endItPoint&=17){}
&&&&&&&&&&&&&&
//当我和庄家的点数都大于17时跳出循环
public int fraction(){
if(endMyPoint&21){
if(endItPoint&21){
}else if(endMyPoint==endItPoint){
if(newPoker[0]+newPoker[2]==21){
if(endMyPoint&endItPoint){
if(endMyPoint&endItPoint){
&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&
//返回得分
[程序结果的分析说明]:
用运行结果制作成的表格:
3+5+4+10=22
3+10+10=23
2+5+9+10=26
10+2+10=22
赢(blackjack)
解释说明:从运行的结果我们可以看到,12次的游戏结果出现了0即“平局”,-2即“我输了”,2即“我赢了”,3即“我拿到只两张牌并靠21点赢了”这四种情况,最后我一共输了5块钱,21点游戏结果可能的所有情况都出现了。经多次调试和实验证明,程序已经可以稳定正常的实现21点游戏的蒙特卡洛模拟。以上只是多次试验结果的一种,蒙特卡洛模拟每次结果都是不同的,虽然这只是对现实生活中21游戏的计算机模拟,但这些数据仍具有很高的可靠性,具有研究价值。
[总结及心得体会]:
不得不说这个项目设计是颇具挑战性的,由于我们团队的成员都是第一次接触这种问题,对解决问题的步骤方法等都只有一个模糊的概念。起初我们分析这个问题后觉得问题并不难,于是早早就开始编写程序,但是由于对问题分析不够透彻,理解不够深刻,编写程序时遇到很多困难,程序不是缺了这个功能,就是那个功能无法正确实现。于是写了一天程序也写不好,最后只能对问题重新分析,并思考这个问题究竟该如何解决,各部分功能该如何实现。当再一次回头看问题时,思路也越发清晰起来,第二次写程序也就比较顺畅了。
在这次项目设计中,我们真正体会到实践的重要性,“纸上得来终觉浅,绝知此事要躬行。”光有理论知识是不能解决实际问题的,必须是我们把理论知识运用到实践中,通过不断的尝试把问题解决。这次设计也体现出了团队合作的优势,团队合作可以取长补短,发挥每个人的长处,这样不仅可以减少很多盲点,而且可以节约很多时间。
在这里,我最大的收获就是得到了一次实训的经验,如何把一个实际问题转化成数学问题,再把数学理论通过编程的实现来解决问题。这次实践不仅锻炼了我解决实际问题的能力,也对我的思维方式颇多启发,遇到问题首先不是入手解决问题,而是要先分析问题,把问题真正吃透了再去入手解决问题。
[参考书目]:
Java语言程序设计(第二版) 李尊朝、苏军(编著)& 中国铁道出版社
Java2核心技术(第6版) (美)Gay S.Horstmann Gary Cornell(著)机械工业出版社
计算机数学基础&&&
王信峰(主编)&&&
高等教育出版社
报告评语及得分:
教师签名:
已投稿到:
以上网友发言只代表其个人观点,不代表新浪网的观点或立场。