题目链接

题意 : 一串数字变成另一串数字,可以单个数字转变,或者一类数字转变,问最少操作次数

分析 :

15年北京赛区的银牌题

首先有一个点需要想明白、或者猜得到

即最优的做法肯定是先做完 2 操作最后用 1 操作

2 操作单次可以改变的字符数远大于 1 操作 ( 当然这个不是证明上面的结论、只是给个灵感去猜

具体操作就是 s2 => 通过 2 操作变成中间状态 => 通过 1 操作变成 s1

对于 2 操作、与具体字符的数量无关、只和种类有关、即从一种数字变成另一种

那么就是一种映射关系、那么我们可以使用一个六位的六进制数来表示不同的状态

首先将字符集全部 -1 、即原来串是由 {1,2,3,4,5,6} 组成变成由 {0,1,2,3,4,5}组成 ( 方便进制转化 )

那么这种映射关系是什么呢?如何表示的 2 操作呢?

比如 012345 => 112345 表示将原来字符所有的 0 变成 1

012345 => 112344 表示将原来字符串所有的 0 变成 1、所有的 5 变成 4

所有对于所有的状态、可以使用 BFS 从初始状态 (012345)6 开始、将它到其他状态的花费求出来

那么就可以统计出所有 2 操作能到达的状态的最小花费了、当然六进制的状态最后要用十进制存储才方便存储

最后就是像刚刚说的那样子、先枚举中间状态(6^6个最多)、然后计算出从中间状态通过 1 操作到达目标状态的花费即可

#include<bits/stdc++.h>
#define LL long long
#define ULL unsigned long long

#define scl(i) scanf("%lld", &i)
#define scll(i, j) scanf("%lld %lld", &i, &j)
#define sclll(i, j, k) scanf("%lld %lld %lld", &i, &j, &k)
#define scllll(i, j, k, l) scanf("%lld %lld %lld %lld", &i, &j, &k, &l)

#define scs(i) scanf("%s", i)
#define sci(i) scanf("%d", &i)
#define scd(i) scanf("%lf", &i)
#define scIl(i) scanf("%I64d", &i)
#define scii(i, j) scanf("%d %d", &i, &j)
#define scdd(i, j) scanf("%lf %lf", &i, &j)
#define scIll(i, j) scanf("%I64d %I64d", &i, &j)
#define sciii(i, j, k) scanf("%d %d %d", &i, &j, &k)
#define scddd(i, j, k) scanf("%lf %lf %lf", &i, &j, &k)
#define scIlll(i, j, k) scanf("%I64d %I64d %I64d", &i, &j, &k)
#define sciiii(i, j, k, l) scanf("%d %d %d %d", &i, &j, &k, &l)
#define scdddd(i, j, k, l) scanf("%lf %lf %lf %lf", &i, &j, &k, &l)
#define scIllll(i, j, k, l) scanf("%I64d %I64d %I64d %I64d", &i, &j, &k, &l)

#define lson l, m, rt<<1
#define rson m+1, r, rt<<1|1
#define lowbit(i) (i & (-i))
#define mem(i, j) memset(i, j, sizeof(i))

#define fir first
#define sec second
#define VI vector<int>
#define ins(i) insert(i)
#define pb(i) push_back(i)
#define pii pair<int, int>
#define VL vector<long long>
#define mk(i, j) make_pair(i, j)
#define all(i) i.begin(), i.end()
#define pll pair<long long, long long>

#define _TIME 0
#define _INPUT 0
#define _OUTPUT 0
clock_t START, END;
void __stTIME();
void __enTIME();
void __IOPUT();
using namespace std;

 + ;
;
 + ;
const int INF = 0x3f3f3f3f;

int to_ten(int c[])///将六进制转十进制
{
    ;
    ; i<; i++){
        ret = ret *  + c[i];
    }return ret;
}

inline void to_six(int num, int c[])///十进制转六进制(存在 c 中)
{
    ; i>=; i--){
        c[i] = num % ;
        num /= ;
    }
}

int Cost[mxState];///存储操作 2 的花费

][];///存储原本 s2 => s1 只通过 1 操作所用的花费
            ///比如 g[1][2] = 3 将 s2 的 1 变成 s1 的 2 只用 1 操作要进行 3 次

];///存储 s2 中每个数字出现的次数

char s1[maxLen], s2[maxLen];

inline void BFS()
{
    ] = {, , , , , };

    int FirState = to_ten(c);
    mem(Cost, INF);
    Cost[FirState] = ;

    queue<int> que;
    que.push(FirState);
    while(!que.empty()){
        int T = que.front(); que.pop();

        to_six(T, c);

        ; i<; i++){
            ; j<; j++){
                ];
                memcpy(tmp, c, sizeof(tmp));
                ; k<; k++)
                    if(tmp[k] == i)
                        tmp[k] = j;

                int newState = to_ten(tmp);

                ){
                    Cost[newState] = Cost[T] + ;
                    que.push(newState);
                }
            }
        }
    }
}

int main(void){__stTIME();__IOPUT();

    BFS();

    while(~scs(s1)){
        scs(s2);
        int len = strlen(s1);
        mem(cnt, );
        mem(g, );
        ; i<len; i++){
            ';
            ';
            cnt[ch2]++;
            g[ch2][ch1]++;
        }

        int ans = INF;
        ];
        ; i<mxState; i++){///枚举中间状态
            to_six(i, c);
            int cost = Cost[i];///将 s2 => 中间状态 的花费
            ; j<; j++)///进行操作 1 的花费计算
                cost += cnt[j] - g[j][c[j]];///举个例子就好理解一点、比如 s1="001" 、s2="112"、用这个例子去模拟
            ans = min(ans, cost);
        }

        printf("%d\n", ans);

    }

__enTIME();;}

void __stTIME()
{
    #if _TIME
        START = clock();
    #endif
}

void __enTIME()
{
    #if _TIME
        END = clock();
        cerr<<"execute time = "<<(double)(END-START)/CLOCKS_PER_SEC<<endl;
    #endif
}

void __IOPUT()
{
    #if _INPUT
        freopen("in.txt", "r", stdin);
    #endif
    #if _OUTPUT
        freopen("out.txt", "w", stdout);
    #endif
}

hihocoder 1251 Today is a rainy day ( 15年北京 C、暴力 )的更多相关文章

  1. 暴力 hihoCoder 1251 Today Is a Rainy Day (15北京C)

    题目传送门 题意:一串数字变成另一串数字,可以单个数字转变,或者一类数字转变,问最少操作次数 分析:首先一类转换比单个转换优,先枚举找出最优的映射方案,然后将零碎的操作加上.6位6进制表示map映射, ...

  2. 【BFS】【枚举】HihoCoder - 1251 - The 2015 ACM-ICPC Asia Beijing Regional Contest - C - Today Is a Rainy Day

    题意:给你两个只由1~6组成的串,问你B串至少要经过几次操作变成A串. 一次操作要么选择一个种类的数,将其全部变成另一种类:要么选择一个数,将其变为另一个数. 可以证明,一定先进行一定数量的第一种操作 ...

  3. hihoCoder 1391 Countries【预处理+排序+优先队列】2016北京网络赛

    题目:http://hihocoder.com/problemset/problem/1391 题目大意: A和B两个国家互射导弹,每个国家都有一个防御系统,在防御系统开启的时间内可以将到达本国的导弹 ...

  4. hihocoder 微软编程之美2015 初赛 第一场 (树算法 + 暴力思想 + 搜索思想)

    题目1 : 彩色的树 时间限制:2000ms 单点时限:1000ms 内存限制:256MB 描述 给定一棵n个节点的树,节点编号为1, 2, …, n.树中有n - 1条边,任意两个节点间恰好有一条路 ...

  5. (中等) Hiho 1232 Couple Trees(15年北京网络赛F题),主席树+树链剖分。

    "Couple Trees" are two trees, a husband tree and a wife tree. They are named because they ...

  6. hihoCoder #1831 : 80 Days-RMQ (ACM/ICPC 2018亚洲区预选赛北京赛站网络赛)

    水道题目,比赛时线段树写挫了,忘了RMQ这个东西了(捞) #1831 : 80 Days 时间限制:1000ms 单点时限:1000ms 内存限制:256MB 描述 80 Days is an int ...

  7. hihoCoder 1185 连通性·三(Tarjan缩点+暴力DFS)

    #1185 : 连通性·三 时间限制:10000ms 单点时限:1000ms 内存限制:256MB 描述 暑假到了!!小Hi和小Ho为了体验生活,来到了住在大草原的约翰家.今天一大早,约翰因为有事要出 ...

  8. 苹果应用商店AppStore审核中文指南 分类: ios相关 app相关 2015-07-27 15:33 84人阅读 评论(0) 收藏

    目录 1. 条款与条件 2. 功能 3. 元数据.评级与排名 4. 位置 5. 推送通知 6. 游戏中心 7. 广告 8. 商标与商业外观 9. 媒体内容 10. 用户界面 11. 购买与货币 12. ...

  9. 【hihocoder 1628】K-Dimensional Foil(线性代数)

    hihocoder 1627 The 2017 ACM-ICPC Asia Beijing Regional Contest 北京区域赛 B.K-Dimensional Foil 题意 给定N个点的前 ...

随机推荐

  1. __declspec(dllexport)的作用

    加了之后发现,用ollydbg导入dll,可以自动判断某个函数是导出函数

  2. Java回调实现异步 (转)

    出处: Java回调实现异步 在正常的业务中使用同步线程,如果服务器每处理一个请求,就创建一个线程的话,会对服务器的资源造成浪费.因为这些线程可能会浪费时间在等待网络传输,等待数据库连接等其他事情上, ...

  3. 推荐系统遇上深度学习(十)--GBDT+LR融合方案实战

    推荐系统遇上深度学习(十)--GBDT+LR融合方案实战 0.8012018.05.19 16:17:18字数 2068阅读 22568 推荐系统遇上深度学习系列:推荐系统遇上深度学习(一)--FM模 ...

  4. django 项目开发及部署遇到的坑

    1.django 连接oracle数据库遇到的坑 需求:通过plsql建立的oracle数据表,想要django操作这几个表 python manage.py inspectdb table_name ...

  5. 关于HA(2.102 -2.103 服务器排障)

    关于处理RHCA故障的报告: ,2.102 和 2.103 两台机器在重启之后拉不起来 原因是这两台服务比较怪 先要启动service rpcbind restart 然后再要起service nfs ...

  6. Javascript——数据类型 和 注释

    数据类型:JavaScript中包括如下7种数据类型:字符串.数字.布尔.数组.对象.null.undefined 字符串: 注意:字符串类型的数据需要使用单引号或双引号引起来. 数字: 注意:Jav ...

  7. Navicat 12的安装与使用(附加破解)

    地址https://blog.csdn.net/tomos428/article/details/80483450?tdsourcetag=s_pctim_aiomsg

  8. 修改git默认的编辑器nano为vim的方法

    git默认的编辑器是nano,使用起来不易操作,下面介绍两种方法将git默认的编辑器修改为vim.  git config --global core.editor vim .git/config文件 ...

  9. task service的ftp和s3同步文件后续优化方案

    1,开启多个task service服务,比如153,154,162各开启一个服务,去ftp和s3读取文件的第一步首先改文件名,比如xxxxxx_153,然后其他154和162不去处理这个文件,xxx ...

  10. 【Swift后台】背景介绍

    在2017年11月的时候,就已经对Swift后台进行过研究,简书上发表过相应文章,那时候发表的是单纯的对Vapor文档的翻译,此次则是作为进一步研究的学习笔记来保存. Swift后台的本质,主要是Va ...