模拟游戏,规则如下
把卡牌一张接一张,从左到右依次摊开,不可以重叠,每当某张卡片和左边(左边第三张)卡片匹配,
它就能放到另外一张卡片上,匹配的规则是他们有一样的级别或者花色,
在每次移动完成以后,还需要再次检查这次移动后是否会造成其他可能的移动,
只有每一叠卡片最上面那张能够移动,如果一叠牌被移空,应该立即将右边各叠整体向左移动,
补上这个空隙,依次将牌发完,并尽可能的向左合并,如果最后只剩下一叠牌,则游戏胜利

多玩几次可能会出现这样的局面,
有俩个卡片可以移动,你应该采取的策略是移动最左边的卡片
如果一张卡片能够移动到左边第一个位置和第三个位置,将它移动到第三个位置上

输入到程序的数据指出了一副牌发出的顺序,输入包括俩行,
每一行包含26个卡片,每个卡片用一个空格隔开,
输入文件的最后一行包含一个#作为它的第一个字符,
一张牌代表俩个字符单元,
第一个字符是面值(A=Ace,2-9,T=10,J=Jack,Q=Queen,K=King)
第二个字符是它的花色,(C=Clubs(梅花),D=Diamonds(钻石),H=Hearts(红心),S=Spades(黑桃))

每俩行(定义了一副52张牌)产生一个输出行,
每个输出行输出经过游戏后,剩下的叠数,每叠牌中的数目

AC代码如下,适用列表,一个Head数组

将tail指针指向数组位置绝对是噩梦

 #include <iostream>
#include<stdio.h>
using namespace std; struct Node
{
Node* next = NULL;
Node* pre = NULL;
//指向最后一个位置,不能是数组的位置
Node* tail = NULL;
char suit;
char face;
int total;
};
bool compareNode(const Node* node1, const Node* node2)
{ return (node1->face == node2->face) || (node1->suit == node2->suit);
}
/**
*
*get a head that node can link.
*if can not find,return NULL
*/
int findSuitableHead(Node* const heads, int total, Node* const node)
{
int index = -;
while (true)
{
bool fh = false;
if (total >= )
{
//可以找前面第三个
Node hNode = heads[total - ];
if (compareNode(hNode.tail, node))
{
total -= ;
index = total;
fh = true;
}
}
if (!fh && total >= )
{
//前三个位置不合适,前一个位置
Node hNode = heads[total - ];
if (compareNode(hNode.tail, node))
{
total -= ;
fh = true;
index = total;
}
}
if (!fh)
{
return index;
}
}
}
void reMegerNode(Node* const heads, int& total, int sIndex)
{
while (true)
{
bool hasResize = false;
for (int i = sIndex + ; i < total; i++)
{
int j = findSuitableHead(heads, i, (heads + i)->tail);
if (j != -)
{
//可以合并
Node* nHead = heads + j;
//这句话fb50
// Node mNode = heads[i];
Node* mNode = new Node;
*mNode = heads[i]; bool nm = heads[i].total == ? true : false;
if (nm)
{
//mNode is head
mNode->total = ;
mNode->tail = NULL;
nHead->tail->next = mNode;
mNode->pre = nHead->tail;
nHead->tail = mNode;
nHead->total++;
total--;
for (int k = i; k < total; k++)
heads[k] = heads[k + ]; Node n;
heads[total] = n;
}
else
{
//不是表头
heads[i].total--;
Node* tail = heads[i].tail;
Node* pre = tail->pre;
heads[i].tail = pre;
pre->next = NULL;
tail->pre = NULL;
nHead->tail->next = tail;
tail->pre = nHead->tail;
nHead->tail = tail;
nHead->total++;
}
sIndex = j == ? : j - ;
hasResize = true;
break;
}
}
if (!hasResize)
{
return;
}
} }
void mergeNode(Node* const heads, int& total, Node* node)
{
int sIndex = findSuitableHead(heads, total, node);
if (sIndex == -)
{
//new head
node->total = ;
heads[total] = *node;
heads[total].tail = node;
total++;
}
else
{
heads[sIndex].tail->next = node;
node->pre = heads[sIndex].tail;
heads[sIndex].tail = node;
heads[sIndex].total++;
reMegerNode(heads, total, sIndex);
}
}
void print(Node* const heads, int total)
{
if(total!=)
cout << total << " piles remaining:";
else
cout << total << " pile remaining:";
for (int i = ; i < total; i++)
{
cout << " " << heads[i].total;
}
cout << endl;
} int main()
{
//freopen("d:\\1.txt", "r", stdin);
char c1;
while (true)
{
Node* node = new Node;
cin >> c1;
if (c1 == '#')
{
return ;
}
node->face = c1;
cin >> node->suit;
int total = ;
Node heads[];
node->total = ;
heads[total++] = *node;
heads[total - ].tail = node;
for (int i = ; i < ; i++)
{
node = new Node;
cin >> node->face >> node->suit;
mergeNode(heads, total, node);
}
print(heads, total);
}
}

UVA127的更多相关文章

  1. [刷题]算法竞赛入门经典(第2版) 6-9/UVa127 - "Accordian" Patience

    题意:52张牌排一行,一旦出现任何一张牌与它左边的第一张或第三张"匹配",即花色或点数相同,则须立即将其移动到那张牌上面,将其覆盖.能执行以上移动的只有压在最上面的牌.直到最后没有 ...

  2. UVa127,"Accordian" Patience

    注意1堆的时候,pile后面没有s!!!!因为这个WA了一次,否则就1A了 犯了一个很幼稚很幼稚的错误,申请ans[]后玩了吧ans置0,结果调了好长好长时间,本来是敲完就能过的T T啊啊啊啊啊啊,一 ...

  3. UVA-127 "Accordian" Patience (模拟)

    题目大意:一种纸牌游戏,将52张扑克牌排成一列,每次操作可将一张扑克牌移到它的前一张或前面第三张上当牌的点数或花色匹配时.每次都移动最靠左的扑克牌,并且能移动三格就移动三格.求最终扑克牌状态. 题目分 ...

  4. ACM学习历程——UVA127 "Accordian" Patience(栈, 链表)

    Description  ``Accordian'' Patience  You are to simulate the playing of games of ``Accordian'' patie ...

  5. UVA-127 "Accordian" Patience(模拟)

    题目: 把52张牌从左到右排好,每张牌自成一个牌堆.当某张牌与它左边那张牌或者左边第三张牌匹配时(花色或者点数相同)时,就把这张牌移到那张牌上面. 移动之后还要查看是否可以进行其他移动.只有位于牌堆顶 ...

  6. 入门经典——基础数据结构专题(List)

    UVA127 链接:https://uva.onlinejudge.org/index.php?option=com_onlinejudge&Itemid=8&page=show_pr ...

  7. UVa 127 纸牌游戏(栈)

    https://vjudge.net/problem/UVA-127 题意: 按从左至右的顺序发牌,并摆成一行,发牌不要相互重叠.游戏中一旦出现任何一张牌与它左边的第一张或第三张“匹配”,即花色或点数 ...

随机推荐

  1. WinRAR的自解压模式 - imsoft.cnblogs

    一个 SFX (SelF-eXtracting)自解压文件是压缩文件的一种,它结合了可执行文件模块,一种用以运行从压缩文件解压文件的模块.这样的压缩文件不需要外部程序来解压自解压文件的内容,它自己便可 ...

  2. centos7 使用mount 挂载window10 (超简单)

    一直使用vmware tools 挂载,发现好多问题,折腾了大半天放弃了,现在使用mount挂载,发现简单多了 一丶首先添加你需要共享的Windows文件夹,右键 记得要选择 Everyone 和一个 ...

  3. idea快捷键 好的网址收藏

    http://blog.csdn.net/u010800804/article/details/48491395http://blog.csdn.net/wei83523408/article/det ...

  4. gem install没有反应 解决办法

    在虚拟机上执行gem install redis 没有反应: 百度方法如下: #移除官方镜像,增加淘宝镜像 gem sources --add https://ruby.taobao.org/ --r ...

  5. FastAdmin 开发时对数据库进行版本管理 (非 think-migration)

    因为开必项目,暂时还不没用 think-migration,先用 脚本处理. 在导出 SQL 时将相关字段数据还原,比如 admin logitime updatetime token. 把 admi ...

  6. JS 的预编译和执行顺序

    脚本执行js引擎做的工作: 语法分析 预编译 解释执行

  7. maven 知识点1

    在POM 4中,dependency 中还引入了 scope,它主要管理依赖的部署.目前 scope 可以使用5个值: compile,缺省值,适用于所有阶段,会随着项目一起发布. provided, ...

  8. button使用注意

    <button type="button" class="btn btn-primary" onclick="ChangePassword(); ...

  9. Linux下Oracle中SqlPlus时上下左右键乱码问题的解决办法

    window下的sqlplus可以通过箭头键,来回看历史命令,用起来非常的方便. 但是在Linux下,会出现各种乱码,非常不方便,如下图所示,每次打错一个字符就需要重新打一遍. 解决办法:rlwrap ...

  10. java学习之路之javaSE基础2

    java学习之路之javaSE基础2 所有的代码都是引用他人写的. 1.逻辑运算符 //&,|,^,! //int x = 10; //5 < x < 15 //x > 5 ...