博客
关于我
强烈建议你试试无所不能的chatGPT,快点击我
vijos 1085 Sunnypig闯三角关
阅读量:6412 次
发布时间:2019-06-23

本文共 2296 字,大约阅读时间需要 7 分钟。

{这个题5个正确,五个超时,不要盲目相信我的代码,谁有更好的算法或者优化请留言,(*^__^*) 嘻嘻……}

背景

贪玩的sunnypig请Charles为他打造一个奇幻世界,Charles欣然答应了。然而一向善于出难题的Charles是决不会轻易让sunnypig轻松拥有一个奇幻世界的,于是Charles在建造过程中设置了重重机关,只有在sunnypig破解了这些障碍之后,才能尝试到奇幻世界中最有玩头的终极宝贝——时空穿梭机。虽然奇幻世界中其他的宝贝也很有趣,但贪玩的sunnypig怎能放过打boss的机会呢?于是他开始了破解障碍的旅程。

描述

第二道障碍来源于一种古老的数学发现——杨辉三角,不过应该是倒过来的杨辉三角。若给出1~n的一个排列A,则将A1、A2相加,A2、A3相加……An-1、An相加,则得到一组n-1个元素的数列B;再将B1、B2相加,B2、B3相加,Bn-2、Bn-1相加,则得到一组n-2个元素的数列……如此往复,最终会得出一个数T。而Charles给sunnypig出的难题便是,给出n和T,再尽可能短的时间内,找到能通过上述操作得到T且字典序最小的1~n的排列。经过汉诺塔问题的训练,sunnypig开始沉着的思考。。。

格式

输入格式

本题有多组数据,对于每组数据:

一行两个整数n(0<n<=20),t即最后求出来的数。

用文件结尾符判断输入结束。

输出格式

对于每组测试数据输出一行n个整数,用空格分开,行尾无多余空格,表示求出来的满足要求的1~n的一个排列。

 

解题思路

由题意得,有两个数a,b时,t=a+b;

              有三个数a,b,c 时 t=a+2b+c

              有四个数a,b,c,d时 t=a+3b+3c+d

              ……

             不难得出,符合杨辉三角

于是,可以枚举每个系数后的值,然后进行相加,做适当的剪枝,可以得出答案

有人说是用排序不等式做,可惜本人是一枚学渣兼蒟蒻,即使看到那个所谓a^2+b^2+c^2>=ab+ac+bc也不知道该怎么用......

 
1 program yanghui; 2 var n,i,j,sum,t,flag:longint; 3     a:array[0..20,0..20] of longint; 4     b:array[0..20] of longint; 5     s:array[0..20] of longint; 6     pd:Array[1..20] of boolean; 7 procedure yanghui;//求出杨辉三角 8 var i,j:longint; 9 begin10  a[1,1]:=1;11  for i:=2 to 20 do12    begin13     for j:=1 to i do14     begin15       a[i,j]:=a[i-1,j]+a[i-1,j-1];16     end;17    end;18 end;19 procedure dfs(n,k:longint);20 var i:Longint;21 begin22     if flag=1 then exit;//如已经有答案,退出23     if sum>t then exit;//如已经超过所求值,退出24     if sum+(s[n]-s[k-1])*n
(n+1) div 2) and(b[n-k+2]>b[k-1]) then exit;//如后面的值比对应位置的值大,退出(因为此时不是字典序最前的值)26 if k=n+1 then27 begin28 if sum=t then29 begin30 for i:=1 to n do write(b[i],' ');31 writeln;32 flag:=1;33 end;34 exit;35 end;36 for i:=1 to n do//简单回溯寻找答案37 if (not pd[i]) then38 begin39 sum:=sum+i*a[n,k];40 b[k]:=i;41 pd[i]:=true;42 dfs(n,k+1);43 if flag=1 then exit;44 sum:=sum-i*a[n,k];45 pd[i]:=false;46 end;47 end;48 49 begin50 yanghui;51 while not eof do52 begin53 fillchar(pd,sizeof(pd),false);54 flag:=0;55 sum:=0;56 read(n,t);57 for i:=1 to n do s[i]:=s[i-1]+a[n,i];//前缀和,表示第n行前i个杨辉三角上的数值之和58 dfs(n,1);59 end;60 end.

 

转载于:https://www.cnblogs.com/wuminyan/p/4725621.html

你可能感兴趣的文章
android 屏幕适配一:通过自定义View的方式实现适配
查看>>
学不好Python?我们分析看看正确的学习方法是什么-马哥教育
查看>>
面向对象复习日志二:Traits
查看>>
我的前端那些事--简介
查看>>
为什么在JavaScript中使用Prototype?[译]
查看>>
教妹学 Java:大有可为的集合
查看>>
微服务治理平台的RPC方案实现
查看>>
android 开发艺术view笔记
查看>>
程序员面试问答集锦,从容应对各种面试难题!
查看>>
你|可以为性感代言
查看>>
[仁润云技术团队]并发编程-(2)并发编程的目标
查看>>
Android 技术选型闲聊
查看>>
在 VS Code 中校验 Jenkinsfile
查看>>
数据结构与算法系列
查看>>
【直通BAT】剑指Offer 经典试题整理(4)
查看>>
Pyhton抓取BOSS直聘职位描述和数据清洗,很简单没有那么难
查看>>
Angular是什么框架?Angular如何入门?该看些什么资料,学习建议
查看>>
移动端网页调试
查看>>
JavaScript 引擎 V8 新机制:JIT-less 模式
查看>>
数据库之事务之间的隔离
查看>>