‘壹’ 常见的几种数组排序算法JS实现
排序,从小大,0坐标的在下面,即排序后小的在下面,大的在上面。
1,冒泡Bubble:从第0个开始,一直往上,与相邻的元素比较,如果下面的大,则交换。
Analysis:
Implementation:
void BubbleSort(int *pData, int iNum)
2,插入Insertion:与打扑克牌时整理牌很想象,假定第一张牌是有序的,从第二张牌开始,拿出这张牌来,往下比较,如果有比这张牌大的,则把它拨到上一个位置,直到找到比手上的这张更小的(或到顶了),
则把手上的这张牌插入到这张更小的牌的后面。
Analysis:
Implementation:
void InsertionSort(int *list, int length)
{
int i, j, temp;
for (i = 1; i < length; i++)
{
temp = list[i];
j = i - 1;
while ((j >= 0) && (list[j] > temp))
{
list[j+1] = list[j];
j--;
}
list[j+1] = temp;
}
}
3,选择Selection:从所有元素中找到最小的放在0号位置,从其它元素(除了0号元素)中再找到最小的,放到1号位置,......。
Analysis:
Implementation:
void SelectionSort(int data[], int count)
{
int i, j, min, temp;
for (i = 0; i < count - 1; i++)
{
/* find the minimum */
min = i;
for (j = i+1; j < count; j++)
{
if (data[j] < data[min])
{
min = j;
}
}
/* swap data[i] and data[min] */
temp = data[i];
data[i] = data[min];
data[min] = temp;
}
}
4,快速Quick:先拿出中间的元素来(值保存到temp里),设置两个索引(index or pointer),一个从0号位置开始往最大位置寻找比temp大的元素;一个从最大号位置开始往最小位置寻找比temp小的元素,找到了或到顶了,则将两个索引所指向的元素
互换,如此一直寻找交换下去,直到两个索引交叉了位置,这个时候,从0号位置到第二个索引的所有元素就都比temp小,从第一个索引到最大位置的所有元素就都比temp大,这样就把所有元素分为了两块,然后采用前面的办法分别排序这两个部分。总的来
说,就是随机找一个元素(通常是中间的元素),然后把小的放在它的左边,大的放右边,对左右两边的数据继续采用同样的办法。只是为了节省空间,上面采用了左右交换的方法来达到目的。
Analysis:
Implementation:
void QuickSort(int *pData, int left, int right)
{
int i, j;
int middle, iTemp;
i = left;
j = right;
middle = pData[(left + right) / 2]; //求中间值
do
{
while ((pData[i] < middle) && (i < right)) //从左扫描大于中值的数
i++;
while ((pData[j] > middle) && (j > left)) //从右扫描小于中值的数
j--;
if (i <= j) //找到了一对值
{
//交换
iTemp = pData[i];
pData[i] = pData[j];
pData[j] = iTemp;
i++;
j--;
}
} while (i <= j); //如果两边扫描的下标交错,就停止(完成一次)
//当左边部分有值(left<j),递归左半边
if(left < j)
QuickSort(pData, left, j);
//当右边部分有值(right>i),递归右半边
if(right > i)
QuickSort(pData, i, right);
}
5,希尔Shell:是对Insertion Sort的一种改进,在Insertion Sort中,从第2个位置开始取出数据,每次都是与前一个(step/gap==1)进行比较。Shell Sort修改为,在开始时采用较大的步长step,
从第step位置开始取数据,每次都与它的前step个位置上的数据进行比较(如果有8个数据,初始step==4,那么pos(4)与pos(0)比较,pos(0)与pos(-4),pos(5)与pos(1),pos(1)与pos(-3),
...... pos(7)与pos(3),pos(3)与pos(-1)),然后逐渐地减小step,直到step==1。step==1时,排序过程与Insertion Sort一样,但因为有前面的排序,这次排序将减少比较和交换的次数。
Shell Sort的时间复杂度与步长step的选择有很大的关系。Shell排序比冒泡排序快5倍,比插入排序大致快2倍。Shell排序比起QuickSort,MergeSort,HeapSort慢很多。但是它相对比较简单,它适合
于数据量在5000以下并且速度并不是特别重要的场合。它对于数据量较小的数列重复排序是非常好的。
Analysis:
Implementation:
template<typename RandomIter, typename Compare>
void ShellSort(RandomIter begin, RandomIter end, Compare cmp)
{
typedef typename std::iterator_traits<RandomIter>::value_type value_type;
typedef typename std::iterator_traits<RandomIter>::difference_type diff_t;
diff_t size = std::distance(begin, end);
diff_t step = size / 2;
while (step >= 1)
{
for (diff_t i = step; i < size; ++i)
{
value_type key = *(begin+i);
diff_t ins = i; // current position
while (ins >= step && cmp(key, *(begin+ins-step)))
{
*(begin+ins) = *(begin+ins-step);
ins -= step;
}
*(begin+ins) = key;
}
if(step == 2)
step = 1;
else
step = static_cast<diff_t>(step / 2.2);
}
}
template<typename RandomIter>
void ShellSort(RandomIter begin, RandomIter end)
{
typedef typename std::iterator_traits<RandomIter>::value_type value_type;
ShellSort(begin, end, std::less<value_type>());
}
6,归并Merge:先将所有数据分割成单个的元素,这个时候单个元素都是有序的,然后前后相邻的两个两两有序地合并,合并后的这两个数据再与后面的两个合并后的数据再次合并,充分前面的过程直到所有的数据都合并到一块。
通常在合并的时候需要分配新的内存。
Analysis:
Implementation:
void Merge(int array[], int low, int mid, int high)
{
int k;
int *temp = (int *) malloc((high-low+1) * sizeof(int)); //申请空间,使其大小为两个已经排序序列之和,该空间用来存放合并后的序列
int begin1 = low;
int end1 = mid;
int begin2 = mid + 1;
int end2 = high;
for (k = 0; begin1 <= end1 && begin2 <= end2; ++k) //比较两个指针所指向的元素,选择相对小的元素放入到合并空间,并移动指针到下一位置
{
if(array[begin1]<=array[begin2])
{
temp[k] = array[begin1++];
}
else
{
temp[k] = array[begin2++];
}
}
if(begin1 <= end1) //若第一个序列有剩余,直接拷贝出来粘到合并序列尾
{
memcpy(temp+k, array+begin1, (end1-begin1+1)*sizeof(int));
}
if(begin2 <= end2) //若第二个序列有剩余,直接拷贝出来粘到合并序列尾
{
memcpy(temp+k, array+begin2, (end2-begin2+1)*sizeof(int));
}
memcpy(array+low, temp, (high-low+1)*sizeof(int));//将排序好的序列拷贝回数组中
free(temp);
}
void MergeSort(int array[], unsigned int first, unsigned int last)
{
int mid = 0;
if (first < last)
{
mid = (first+last)/2;
MergeSort(array, first, mid);
MergeSort(array, mid+1,last);
Merge(array,first,mid,last);
}
}
‘贰’ 苏州麻将的胡牌算法
苏州麻将成牌后,给付多少钱由花的多少来决定,花是累计的;
例如:有人清一色七对,5个花,自摸后,应该算花:
清一色10+七对15+成牌5+花5*2+自摸=120;
如果按5银子/花算,那么每人应该给付40*5=200银子;
如果是谁出冲,则由他一人给付200银子;
逃跑:玩家逃跑扣基础分(银子)*120个花
具体算法如下:
1、底:5花
2、硬花:指中发白,梅兰竹菊,春夏秋冬,4百搭,4大白板,每个1花
3、明杠:1花(筒万条)
4、暗杠:2花(筒万条4个一样的在手上选择的杠)
5、字碰:1花(东南西北碰)
6、暗刻:2花(东南西北3个牌在手上)
7、字明杠:3花(东南西北杠)
8、字暗杠:4花(东南西北在手上选择杠)
9、小门清:5花(不吃不碰不明杠)
10、大门清:10花(没有风碰,杠,暗刻,没有硬花)
11、对对胡:5花(以对子的方式构成胡牌,能碰出杠出胡牌,也能不吃不碰胡出,手上以暗刻方式)
12、混一色:5花(一色牌加字牌胡出)
13、七对子:10花(手上胡出,必须有7个对子)
14、清一色:10花(一色牌)
15、杠开(摸花杠,胡牌叫花开,明暗杠,胡牌叫杠开):5花(摸花和明暗杠,从杠头上摸上的牌胡牌)
16、包饺子:一人支付3倍费用(放给玩家杠,此杠牌玩家杠开),算杠开
17、抢杠:一人支付3倍费用(有玩家碰了一对,然后摸牌杠此牌,这时有玩家可以胡这个牌),可以多人抢杠,每家都付3倍费用,小牌遵循3花以上(包括3花,抢杠当自摸),才能抢杠。
18、大吊车:5花(玩家碰杠后,手上只剩1张牌时胡牌)
19、天胡:50花(庄起手14张牌,在没打任何牌之前胡牌)
20、地胡:50花(闲起手13张牌,摸第一张牌的时候胡牌)
21、海底捞月:5花(玩家摸最后一张牌胡牌)
‘叁’ 跪求福清麻将全套规则,包括怎么拿牌,以及所有胡牌的方法算法.查了好多地方都没个详细的规则.
该麻将规则沿用了四川麻将血战到底的基本打法。在麻将牌中去掉了“中,发,白”的字牌,去掉了“东,南,西,北”的风牌。只剩下筒,条,万,三色牌一共108张。麻将的打法按照当前流行的十三张打法。
主要优势:
血流成河的麻将术语:
狗子刨坑,越跑越深:意思就是花猪:也叫三花,打完牌后手上的牌筒条万三种牌都有,就叫花猪。吃包子:打完牌后没有下叫的人,要给已经下叫和胡牌的人赔钱,赔数按照所做牌型番数的最大番数对被查叫方进行赔偿。杠进杠出:每次杠牌输赢都加番(现实中也有杠进不杠出的规则,就是赢牌算番,输不算番)。
‘肆’ 谁能帮我算一下一副牌摸到三张一样的概率为多少 顺便说一下算法 谢谢!
正确答案是(3/51)×(2/50)=1/425。一共52张牌,第一张随便抽,不妨假设抽到5(随便是几都行),那还剩51张牌,5还有3张,第二次抽到5的概率为3/51,假设等二次抽中,那还剩50张牌,5有2张,第三次抽中概率为2/50,再和3/50相乘即可。(信我必对,我高中概率班级前三)
‘伍’ 麻将是怎么算胡
不同地区的胡牌有稍微不同,但是总体规则如下:
缺门可胡。不能吃牌。杠牌补下一张牌。一家胡了并不结束这局,未胡的玩家继续打,直到有三家胡牌或摸牌结束时游戏结束。若牌摸完时有两家或以上未胡牌,此时查叫,无叫的给有叫的赔叫。
1、庄家十四张,先出牌,闲家每人十三张牌。
2、可碰、可杠、不能吃。碰、杠后的牌要亮出牌面(即使是暗杠也要全部亮出牌面)。没有“门前清”这个概念。
3、放炮的一个人负责,与其他人无关。
4、杠牌后补下一张牌。
5、别人打出牌时若放弃胡牌,在同一圈内不能胡另一人打出的相同的牌直到自己摸牌,但不相同的可以胡。如胡25万,下家打2万不胡,对家打2万也不能胡,但打5万可以胡。
6、杠上炮时,点炮者将刚杠所得转移给被点炮者。若杠后点炮超过一响,点炮者要另赔出刚杠所得的点数给被点者。
相关术语
血战到底:一家胡了并不结束这局,而是未胡的玩家继续打,直到有三家都胡或者余下的玩家摸完牌。这样先胡的不一定获利最多,点炮的也能翻身,提高了博弈性和趣味性。牌局结束,一并结算。
刮风下雨:杠在结算时算钱。
庄家:第一局随意,以后每一局由上一局第一个胡牌者当庄,若是一炮双响或一炮三响,由放炮者当庄。
甩色子:由庄家掷两枚骰子以确定端牌的起始位置。
跳牌:庄家摸第14张牌时需隔一沓牌摸上面一张,此谓跳牌。
定张:在一局的开始定下不要哪门牌,以后不能改。一般将一张此颜色的牌面朝下摆放,第一轮打出。
缺(天缺):一局开始摸上牌后就只有两门牌甚至一门牌,此时报缺。
搭子(坎):三张数字连续的牌或三张相同的牌称为一个搭子或一坎牌。
‘陆’ 推倒胡各种胡怎么算钱
根据番数的,不同牌型有不同番数算法,具体如下:
一、屁和(1番)底金×1
二、对对和(2番)底金×2
三、门前清对对和(5番)底金×5
四、明杠(+1番)底金×2
五、暗杠(+1番)底金×2
六、抢杠和(+2番)底金×4
七、杠上花(+2番)底金×4
八、清一色(4番)底金×4
九、清对对胡(8番)底金×8
十、门前清清一色(8番)底金×8
十一、包赔清一色(12番)底金×4×3
十二、包赔对对胡清一色(24番)底金×8×3
十三、七对(4番)底金×4
十四、龙七对(8番)底金×8
十五、双龙七对(16番)底金×16
十六、三龙七对(64番)底金×64
十七、清七对(32番)底金×32
十八、清龙七对(64番)底金×64
十九、清双龙七对(128番)底金×128
二十、清三龙七对(256番)底金×256
可把麻将技巧分为上中下三级。
(一)抓进六筒不会换出九筒的譬如有七、八、九筒一顺,抓进一张六筒仍打六筒——这类人的麻将技巧仅能管理现成的牌,而换一张打的念头还不能产生。当然,听三交而不听,生熟张不甚明了之类的毛病也包括在内。这是下级。
(二)抓进六筒会打九筒的同前例,能换打九筒,说明已看清九筒是大幺,比较地不易给人家便宜。他已经了解生熟张之别,在全副牌的过程中,可不至于蚀搭。这是中级。
(三)抓进九筒而换打六筒的同前例,能这样打,说明水准更高了,因为他抓进一张九筒,而知九筒是生张,六筒的危险倒少,已能解除幺、九熟于中心张子的死限制,这显然是更进一级的技巧了。他不但能看透生张的分别、而且还会因时制宜,随机应变,已到出神入化的地步了。这是上级。
‘柒’ 打麻将如何算牌
1,要知彼,先知己。随时能够看清自己的手牌,除了起手牌要会快速整理以外,更多的体现在摸牌进张时,能够快速判断自己应该打哪一张才有利于进张最宽。这个是经验来的,打多了很容易就会的。
2,知己后知彼。接着,要学会判断接下来自己的进张概率有多少 ,是在牌池中,还是在别人手上。例如,自己需要5万,那我们先判断剩余5条的张数,再去分析对手打34万,或者67万的情况,以此来判断是否在对手手上,毕竟这种可以跟邻牌靠张的还算好判断一些。
3,计算和牌番型。我们在有多种听牌选择时,要学会判断哪种牌型番值比较高,或者是哪种牌型容易胡的,根据目的不同,从而去决定做牌思路,这个也是需要训练的,毕竟平时大家娱乐时还是少用到的,锻炼时间就少了。最后还是跟大家强调,麻将终究是外物,要适当娱乐,拒绝赌博,做个生活健康的人。
打麻将的技巧:
1、一副碰一副一搭
玩牌常常遇到一种情况,副子多一张,可挂搭也可碰,碰了即是碰啥还要啥,如三三四五万,碰了三万还要三六万。要看实际情况而定。一是看搭子够不够。你手中之牌搭子不够,多余闲张又多是边沿张和风字,不好挂搭,应该碰;搭子够,甚至搭子不太好,一般不应该碰。
二是看方位。如果庄家很兴,况且已经连庄,碰了可隔空庄家,那就应该碰牌,起到制控庄家的作用。如果是你的下手打牌,可以碰;上手打牌,应该揭牌而不考虑碰。三看是否停口。如果碰了可以停口,就应该碰;如果是上张停口牌,碰了还不停口,那就一般应揭牌不应该碰。
2、点炮有技巧,防大不防小
实战中,点炮时常发生。点炮的原因有多种,几局牌打下来,不点炮的可能是零。因此,从心理上,不能把点炮视为大忌或重负。如果背着沉重的包袱打牌,那就像蜗牛爬行,永远也难走到胜利的前沿。
点炮有个原则,当自己牌力强时,特别是有大牌时,只要不给做大牌家点炮,生张、险张该拼还是要拼的。俗话说:“敢打敢闯,神清气爽。”“一拼一博,端掉一窝。”实战中,紧要关头,往往就是狭路相逢,必死则生。
3、舍牌三招,时刻记牢
舍牌有三个基本功,一是舍牌要隐蔽,舍牌过程中,要隐蔽意图,不能让对手窥测到你的做牌方向;二是舍牌会引诱,通过舍牌,制造骗局,勾引对手打出自己需要的牌;三是出牌讲究牵制,什么时候让吃,什么时候让碰,扣住什么牌,先出什么牌,后出什么牌,都要把握分寸。
‘捌’ 麻将的算法公式麻将的算法公式
一分钟学会麻将的数学公式:nAAA+mABC+DD就赢了,mn可以等于0。
AAA就是三个一样的牌,ABC就是顺子,DD就是对子。mn可以为0,这句话得用高中数学来理解:mm中可以至少有1个为0。
实例分析:
发牌一开始拿到手,庄家14张牌,闲家13张牌。想要胡,就在接下来摸牌、打牌、对吃杠的过程中想办法使这13张牌符合nAAA+mABC+DD的规律。注意:东南西北中发白这7张牌不能组成ABC的形式,只能组成AAA。
-摸牌、打牌庄家先打一张不摸牌。轮到闲家,先摸一张牌,再打一张。再轮到下一个人。主要是把手上不利于组成公式的牌打掉。
吃、对(碰)、杠:
我有5条和6条。这时,如果我的上家出7条或者4条,那我就可以叫“吃”。通用规律是:
当上家出的牌可以帮我组成顺子ABC形式时;
其他人没有叫“对(碰)、杠、胡”
以上条件同时满足,就可以叫“吃”。然后把这对顺子拿出来,平放在旁边。
听牌、胡牌:
经过以上步骤之后,最终会里标准公式差一张牌。这时就叫听牌。如上图,我有两个AAA型,即m=2。它们是:三个东风,三个发财。这两个放在旁边的,就是我对来的。最右边有1个ABC型,它是7条8条9条。其次是一个DD型——两个八万。注意,有且只能有一个DD。
还有两张单牌,3万和5万。这时,我只要摸一张4万,或者我的上家出一张4万,我就可以胡牌了。最终我胡牌的公式就是2AAA+2ABC+DD。