邮局(深搜+剪枝)

题目如下:

问题描述
  C村住着n户村民,由于交通闭塞,C村的村民只能通过信件与外界交流。为了方便村民们发信,C村打算在C村建设k个邮局,这样每户村民可以去离自己家最近的邮局发信。

  现在给出了m个备选的邮局,请从中选出k个来,使得村民到自己家最近的邮局的距离和最小。其中两点之间的距离定义为两点之间的直线距离。
输入格式
  输入的第一行包含三个整数n, m, k,分别表示村民的户数、备选的邮局数和要建的邮局数。
  接下来n行,每行两个整数x, y,依次表示每户村民家的坐标。
  接下来m行,每行包含两个整数x, y,依次表示每个备选邮局的坐标。
  在输入中,村民和村民、村民和邮局、邮局和邮局的坐标可能相同,但你应把它们看成不同的村民或邮局。
输出格式
  输出一行,包含k个整数,从小到大依次表示你选择的备选邮局编号。(备选邮局按输入顺序由1到m编号)
样例输入
5 4 2
0 0
2 0
3 1
3 3
1 1
0 1
1 0
2 1
3 2
样例输出
2 4
数据规模和约定
  对于30%的数据,1<=n<=10,1<=m<=10,1<=k<=5;
  对于60%的数据,1<=m<=20;
  对于100%的数据,1<=n<=50,1<=m<=25,1<=k<=10。

这道题使用的方法是剪枝+深搜。
解题步骤在于:
先设定一个邮局是已确定的,得出所有的村民到该邮局的距离。
再逐个进行判断未确定的邮局,如果该邮局到所有村民家的距离都大于当前最小值,那么该邮局被剪枝,即被放弃。
直到找遍所有的邮局且邮局数目为当前数目。
使用方法深搜则在于,每当确定一个邮局,那么下一个参数的传递值则加一,来标记已确定邮局数目。
其中需要注意到的是,从大到小首先确定一个数,然后从大到小依次判断是否可留,如果是,那么替换当前已确定最小数,否则,被剪枝。继续迭代。

#include<iostream>  //邮局  
#include<stdlib.h>
#include<math.h>
using namespace std;
int n, m, k, j, c[55][2], y[27][2], d[12], f1, f2, f[55] = { 0 };
float yc[27][55], s = 1000000000;
int dfs(int t, int i, int o[12], float w[55], float sum)
{
    if (i <= m + 1)//如果还没有遍历完所有的邮局
    {
        if (t == k)//如果已经确定的邮局数已足够
        {
            if (sum<s)
            {
                s = sum;//s是最后的最小距离总值
                for (j = 0; j<k; j++)
                    d[j] = o[j];//将数组o的k个值存入数组d
            }
        }
        else if (i <= m&&t<k)//还没有确定所有邮局数
        {
            float ww[55];
            for (j = 1; j <= n; j++)
                ww[j] = w[j];
            dfs(t, i + 1, o, w, sum); f1 = 1, f2 = 0;//下一个邮局,初始化两个标记用的变量f1,f2
            if (!f[i])//f[i]==0,还没有被剪掉
            {
                o[t] = i;//第t个已确定邮局是i
                if (t>0)//ww初始化已经
                {
                    f2 = 1;
                    for (j = 1; j <= n; j++)
                    {
                        if (ww[j]>yc[i][j])//如果邮局到村民家的距离小于当前最小
                        {
                            sum = sum - ww[j] + yc[i][j];//更新
                            ww[j] = yc[i][j];
                            f1 = 0;//变化,不剪掉当前邮局
                        }
                    }
                }
                else//还没有初始化
                {
                    for (j = 1; j <= n; j++)
                    {
                        sum += yc[i][j];
                        ww[j] = w[j] = yc[i][j];//初始化最小值就是当前值
                    }
                } 
                if (f1&&f2)//已经有过ww初始化且需要剪掉当前的邮局,ww如果未初始化那么一定不能剪掉
                {
                    f[i] = 1;//经过处理,已经被剪掉
                    dfs(t, i + 1, o, w, sum);//下一次迭代t不增加
                }
                else
                    dfs(t + 1, i + 1, o, ww, sum);//下一次迭代
            }
        }
    }
}
int main()
{
    int i, j, o[12];
    float w[55], ww[55];
    cin >> n >> m >> k;
    for (i = 1; i <= n; i++)
        cin >> c[i][0] >> c[i][1];
    for (i = 1; i <= m; i++)
    {
        cin >> y[i][0] >> y[i][1];
        for (j = 1; j <= n; j++)
            yc[i][j] = sqrt((c[j][0] - y[i][0])*(c[j][0] - y[i][0]) + (c[j][1] - y[i][1])*(c[j][1] - y[i][1]));
    }//yc[i][j]代表第i个邮局到第j个村民家的距离
    dfs(0, 1, o, w, 0);
    for (i = 0; i<k; i++)
        cout << d[i] << " ";
    return 0;
}
最后编辑于
©著作权归作者所有,转载或内容合作请联系作者
  • 序言:七十年代末,一起剥皮案震惊了整个滨河市,随后出现的几起案子,更是在滨河造成了极大的恐慌,老刑警刘岩,带你破解...
    沈念sama阅读 204,684评论 6 478
  • 序言:滨河连续发生了三起死亡事件,死亡现场离奇诡异,居然都是意外死亡,警方通过查阅死者的电脑和手机,发现死者居然都...
    沈念sama阅读 87,143评论 2 381
  • 文/潘晓璐 我一进店门,熙熙楼的掌柜王于贵愁眉苦脸地迎上来,“玉大人,你说我怎么就摊上这事。” “怎么了?”我有些...
    开封第一讲书人阅读 151,214评论 0 337
  • 文/不坏的土叔 我叫张陵,是天一观的道长。 经常有香客问我,道长,这世上最难降的妖魔是什么? 我笑而不...
    开封第一讲书人阅读 54,788评论 1 277
  • 正文 为了忘掉前任,我火速办了婚礼,结果婚礼上,老公的妹妹穿的比我还像新娘。我一直安慰自己,他们只是感情好,可当我...
    茶点故事阅读 63,796评论 5 368
  • 文/花漫 我一把揭开白布。 她就那样静静地躺着,像睡着了一般。 火红的嫁衣衬着肌肤如雪。 梳的纹丝不乱的头发上,一...
    开封第一讲书人阅读 48,665评论 1 281
  • 那天,我揣着相机与录音,去河边找鬼。 笑死,一个胖子当着我的面吹牛,可吹牛的内容都是我干的。 我是一名探鬼主播,决...
    沈念sama阅读 38,027评论 3 399
  • 文/苍兰香墨 我猛地睁开眼,长吁一口气:“原来是场噩梦啊……” “哼!你这毒妇竟也来了?” 一声冷哼从身侧响起,我...
    开封第一讲书人阅读 36,679评论 0 258
  • 序言:老挝万荣一对情侣失踪,失踪者是张志新(化名)和其女友刘颖,没想到半个月后,有当地人在树林里发现了一具尸体,经...
    沈念sama阅读 41,346评论 1 299
  • 正文 独居荒郊野岭守林人离奇死亡,尸身上长有42处带血的脓包…… 初始之章·张勋 以下内容为张勋视角 年9月15日...
    茶点故事阅读 35,664评论 2 321
  • 正文 我和宋清朗相恋三年,在试婚纱的时候发现自己被绿了。 大学时的朋友给我发了我未婚夫和他白月光在一起吃饭的照片。...
    茶点故事阅读 37,766评论 1 331
  • 序言:一个原本活蹦乱跳的男人离奇死亡,死状恐怖,灵堂内的尸体忽然破棺而出,到底是诈尸还是另有隐情,我是刑警宁泽,带...
    沈念sama阅读 33,412评论 4 321
  • 正文 年R本政府宣布,位于F岛的核电站,受9级特大地震影响,放射性物质发生泄漏。R本人自食恶果不足惜,却给世界环境...
    茶点故事阅读 39,015评论 3 307
  • 文/蒙蒙 一、第九天 我趴在偏房一处隐蔽的房顶上张望。 院中可真热闹,春花似锦、人声如沸。这庄子的主人今日做“春日...
    开封第一讲书人阅读 29,974评论 0 19
  • 文/苍兰香墨 我抬头看了看天上的太阳。三九已至,却和暖如春,着一层夹袄步出监牢的瞬间,已是汗流浃背。 一阵脚步声响...
    开封第一讲书人阅读 31,203评论 1 260
  • 我被黑心中介骗来泰国打工, 没想到刚下飞机就差点儿被人妖公主榨干…… 1. 我叫王不留,地道东北人。 一个月前我还...
    沈念sama阅读 45,073评论 2 350
  • 正文 我出身青楼,却偏偏与公主长得像,于是被迫代替她去往敌国和亲。 传闻我的和亲对象是个残疾皇子,可洞房花烛夜当晚...
    茶点故事阅读 42,501评论 2 343

推荐阅读更多精彩内容

  • 决策树理论在决策树理论中,有这样一句话,“用较少的东西,照样可以做很好的事情。越是小的决策树,越优于大的决策树”。...
    制杖灶灶阅读 5,832评论 0 25
  • 机器学习 经验 数据 数据中产生模型model 的算法 学习算法 learning algorithm 数据集 d...
    时待吾阅读 3,956评论 0 3
  • 一.朴素贝叶斯 1.分类理论 朴素贝叶斯是一种基于贝叶斯定理和特征条件独立性假设的多分类的机器学习方法,所...
    wlj1107阅读 3,070评论 0 5
  • 也许每个人心里想法都不一样,但是我希望有人看到这句话,你们可以好好听对方讲完自己内心的想法。然后再来否定他的想法
    叔懒阅读 124评论 0 0
  • @杨磊老师  “礼乐皆得谓之有德。德者,得也。”《礼记·乐记》篇。 《礼记·中庸》:“故大德必得其位,必得其禄,必...
    杨蕾001阅读 475评论 0 0