dfs+简易剪枝+简易a*

思路:

dfs+简易剪枝+简易a(我也不知道算不算a);

dfs参数记录层数

按消耗牌多少的贪心顺序搜索

有几种情况可以不用搜索(但我还是搜索了)

可以用a*估算出来

最后剩下有单牌,对子,三张牌,4炸弹的时候可以直接算出来;

还有一个剪枝,一个简简单单的剪枝(if(x>=ans) return;);

这个因为省略了很多情况所以并不很慢;

反正我是过了;

代码:

#include<cstdio>
#include<cstring>
#include<iostream>
using namespace std;
int n,jk,kl,ai,bi,hand[],ans=0x7fffffff;
int t,c[];
int A_star() {
memset(c,,sizeof(c));
int tot=,kll=;
for(int i=; i<=; i++) c[hand[i]]++; //统计当前还剩的牌数
while(c[]&&c[]>) c[]--,c[]-=,tot++;//四带一对
while(c[]&&c[]>) c[]--,c[]-=,tot++;//四带两单
while(c[]&&c[]) c[]--,c[]--,tot++;//三带二
while(c[]&&c[]) c[]--,c[]--,tot++;//三带一
for(int i=; i<=; i++) kll+=c[i];
return tot+kll;//带牌+三张 对子 单张
}
void dfs(int x) {
// num=min(num,ans);
// printf("%d %d ",x,ans);
// for(int i=1;i<=15;i++) printf("%d ",hand[i]);
// printf("\n");
if(x>=ans) return;
int pd=;
int cur=; for(int i=; i<=; i++) { //四带两对
if(hand[i]>=) {
hand[i]-=;
for(int j=; j<=; j++) {
if(j!=i&&hand[j]>=) {
hand[j]-=;
for(int v=; v<=; v++) {
if(hand[v]>=&&v!=j) {
hand[v]-=;
// printf("1 ");
dfs(x+);
hand[v]+=;
}
}
hand[j]+=;
}
}
hand[i]+=;
}
}
for(int i=; i<=; i++) { //四带二单
if(hand[i]>=) {
hand[i]-=;
for(int j=; j<=; j++) {
if(j!=i&&hand[j]>=) {
hand[j]-=;
for(int v=; v<=; v++) {
if(hand[v]>=&&v!=i) {
hand[v]-=;
/// printf("2 ");
dfs(x+);
hand[v]+=;
}
}
hand[j]+=;
}
}
hand[i]+=;
}
}
for(int i=; i<=; i++) { //三顺
cur=;
if(hand[i]>=&&i<=) {
for(int j=i; j<=; j++) {
if(hand[j]>=) cur++;
else break;
}
for(int j=cur; j>=; j--) {
for(int v=i; v<=j+i-; v++) hand[v]-=;
// printf("3 ");
dfs(x+);
for(int v=i; v<=j+i-; v++) hand[v]+=;
}
}
}
for(int i=; i<=; i++) { //二顺
cur=;
if(hand[i]>=&&i<=) {
for(int j=i; j<=; j++) {
if(hand[j]>=) cur++;
else break;
}
for(int j=cur; j>=; j--) {
for(int v=i; v<=j+i-; v++) hand[v]-=;
// printf("4 ");
dfs(x+);
for(int v=i; v<=j+i-; v++) hand[v]+=;
}
}
}
for(int i=; i<=; i++) { //一顺
cur=;
if(hand[i]>=&&i<=) {
for(int j=i; j<=; j++) {
if(hand[j]>=) cur++;
else break;
}
for(int j=cur; j>=; j--) {
for(int v=i; v<=j+i-; v++) hand[v]-=;
// printf("5 ");
dfs(x+);
for(int v=i; v<=j+i-; v++) hand[v]+=;
}
}
}
for(int i=; i<=; i++) { //三带二
if(hand[i]>=) {
hand[i]-=;
for(int j=; j<=; j++) {
if(j!=i&&hand[j]>=) {
hand[j]-=;
// printf("6 ");
dfs(x+);
hand[j]+=;
}
}
hand[i]+=;
}
}
for(int i=; i<=; i++) { //三带一
if(hand[i]>=) {
hand[i]-=;
for(int j=; j<=; j++) {
if(j!=i&&hand[j]>=) {
hand[j]-=;
// printf("7 ");
dfs(x+);
hand[j]+=;
}
}
hand[i]+=;
}
}
if(hand[]>=&&hand[]>=) {
hand[]--;
hand[]--;
// printf("8 ");
dfs(x+);
hand[]++;
hand[]++;
}
jk=A_star();
if(x+jk>=ans) return;
else ans=x+jk;
} int main() {
scanf("%d%d",&t,&n);
while(t--) {
memset(hand,,sizeof(hand));
ans=0x7fffffff;
for(int i=; i<=n; i++) {
cin>>ai>>bi;
if(ai!=) {
if(ai>=) hand[ai-]++;
else hand[+ai]++;
} else {
if(bi==) hand[]++;
else hand[]++;
}
}
// for(int i=1;i<=15;i++) printf("%d ",hand[i]);
// printf("\n");
dfs();
printf("%d\n",ans);
}
return ;
}

斗地主,感觉写完这个代码我都成了斗地主大神了。

题解 P2668 【斗地主】的更多相关文章

  1. 洛谷P2668 斗地主==codevs 4610 斗地主[NOIP 2015 day1 T3]

    P2668 斗地主 326通过 2.6K提交 题目提供者洛谷OnlineJudge 标签搜索/枚举NOIp提高组2015 难度提高+/省选- 提交该题 讨论 题解 记录 最新讨论 出现未知错误是说梗啊 ...

  2. Luogu P2668 斗地主(NOIP2015)

    还记得那道我只用特判得了30分的"斗地主"吗? 我今天脑抽打算把它改A掉.为什么不用这大好时光去干些更有意义的事 于是我就挖了这个坑. 题解: 题目链接:P2668 斗地主 本题就 ...

  3. 洛谷P2668 斗地主 [NOIP2015]

    题目描述 牛牛最近迷上了一种叫斗地主的扑克游戏.斗地主是一种使用黑桃.红心.梅花.方片的A到K加上大小王的共54张牌来进行的扑克牌游戏.在斗地主中,牌的大小关系根据牌的数码表示如下:3<4< ...

  4. [NOIP2015] 提高组 洛谷P2668 斗地主

    题目描述 牛牛最近迷上了一种叫斗地主的扑克游戏.斗地主是一种使用黑桃.红心.梅花.方片的A到K加上大小王的共54张牌来进行的扑克牌游戏.在斗地主中,牌的大小关系根据牌的数码表示如下:3<4< ...

  5. P2668 斗地主

    题目描述 牛牛最近迷上了一种叫斗地主的扑克游戏.斗地主是一种使用黑桃.红心.梅花.方片的AAA到KKK加上大小王的共545454张牌来进行的扑克牌游戏.在斗地主中,牌的大小关 系根据牌的数码表示如下: ...

  6. P2668 斗地主 dp+深搜版

    题目描述 牛牛最近迷上了一种叫斗地主的扑克游戏.斗地主是一种使用黑桃.红心.梅花.方片的A到K加上大小王的共54张牌来进行的扑克牌游戏.在斗地主中,牌的大小关系根据牌的数码表示如下:3<4< ...

  7. P2668 斗地主 贪心+深搜

    题目描述 牛牛最近迷上了一种叫斗地主的扑克游戏.斗地主是一种使用黑桃.红心.梅花.方片的A到K加上大小王的共54张牌来进行的扑克牌游戏.在斗地主中,牌的大小关系根据牌的数码表示如下:3<4< ...

  8. 洛谷P2668斗地主(搜索)noip2015

    题目描述 牛牛最近迷上了一种叫斗地主的扑克游戏.斗地主是一种使用黑桃.红心.梅花.方片的A到K加上大小王的共54张牌来进行的扑克牌游戏.在斗地主中,牌的大小关系根据牌的数码表示如下:3<4< ...

  9. 洛谷—— P2668 斗地主

    https://www.luogu.org/problem/show?pid=2668 题目描述 牛牛最近迷上了一种叫斗地主的扑克游戏.斗地主是一种使用黑桃.红心.梅花.方片的A到K加上大小王的共54 ...

随机推荐

  1. .net core EF Core 视图的应用

    由之前的一篇文章<.net core Entity Framework 与 EF Core>我们都已经知道 EF Core 增加了许多特性,并且性能上也有了很大的提升. 但是EF Core ...

  2. KVM virsh console

    (1) 查看正在运行的虚拟机 root@kvm:~# virsh list Id Name State ------------------------------------------------ ...

  3. C#循环结构

    一.背景: 因编程的基础差,因此最近开始巩固学习C#基础,后期把自己学习的东西,总结相应文章中,有不足处请大家多多指教. 二.简介 有的时候,可能需要多次执行同一块代码.一般情况下,语句是顺序执行的: ...

  4. python数据分析&挖掘,机器学习环境配置

    目录 一.什么是数据分析 1.这里引用网上的定义: 2.数据分析发展与组成 3.特点 二.python数据分析环境及各类常用分析包配置 1.处理的数据类型 2.为什么选择python 三.python ...

  5. Java生鲜电商平台-库存管理设计与架构

    Java生鲜电商平台-库存管理设计与架构 WMS的功能: 1.业务批次管理 该功能提供完善的物料批次信息.批次管理设置.批号编码规则设置.日常业务处理.报表查询,以及库存管理等综合批次管理功能,使企业 ...

  6. 开发技术--浅谈python数据类型

    开发|浅谈python数据类型 在回顾Python基础的时候,遇到最大的问题就是内容很多,而我的目的是回顾自己之前学习的内容,进行相应的总结,所以我就不玩基础了,很多在我实际生活中使用的东西,我会在文 ...

  7. 面向对象的六大原则之 接口隔离原则——ISP

    ISP = Interface Segregation Principle   ISP的定义如下: 1.客户端不应该依赖他不需要的接口 2.一个类对另外一个类的依赖性应该是建立在最小的接口上 3.不应 ...

  8. PHP 数组函数大全

    PHP数组函数是核心的一部分.无需安装即可使用这些函数 函数名称 描述 array_change_key_case 将数组中的所有键名修改为全大写或小写 array_chunk 将一个数组分割成多个 ...

  9. uni-app学习心得和填坑,关于uni-app 打包h5 页面的坑

    第一次使用博客园写博客 1.我写博客的原因,梳理知识,整理思路,好记性不如烂笔头做个记录吧!记录生活! 1.了解 大概在我使用hbuilder的时候,在官网浏览下载的hbuilder时候无意中发现了u ...

  10. Windows动态链接库:dll与exe相互调用问题

    本文回顾学习一下Windows动态链接库:dll与exe相互调用问题.一般滴,exe用来调用dll中的类或函数,但是dll中也可以调用exe中的类或函数,本文做一些尝试总结. dll程序: Calcu ...