11届国赛python试题 J: 蓝跳跳

Python010

11届国赛python试题 J: 蓝跳跳,第1张

【问题描述】

小蓝制作了一个机器人,取名为蓝跳跳,因为这个机器人走路的时候基本靠跳跃。

蓝跳跳可以跳着走,也可以掉头。蓝跳跳每步跳的距离都必须是整数,每步可以跳不超过 k 的长度。由于蓝跳跳的平衡性设计得不太好,如果连续两次都是跳跃,而且两次跳跃的距离都至少是 p,则蓝跳跳会摔倒,这是小蓝不愿意看到的。

小蓝接到一个特别的任务,要在一个长为 L 舞台上展示蓝跳跳。小蓝要控制蓝跳跳从舞台的左边走到右边,然后掉头,然后从右边走到左边,然后掉头,然后再从左边走到右边,然后掉头,再从右边走到左边,然后掉头,如此往复。为了让观者不至于太无趣,小蓝决定让蓝跳跳每次用不同的方式来走。小蓝将蓝跳跳每一步跳的距离记录下来,按顺序排成一列,显然这一列数每个都不超过 k 且和是 L。这样走一趟就会出来一列数。如果两列数的长度不同,或者两列数中存在一个位置数值不同,就认为是不同的方案。

请问蓝跳跳在不摔倒的前提下,有多少种不同的方案从舞台一边走到另一边。

【输入格式】

输入一行包含三个整数 k, p, L。

【输出格式】

输出一个整数,表示答案。答案可能很大,请输出答案除以 20201114 的余数。

【样例输入】

3 2 5

【样例输出】

9

【样例说明】

蓝跳跳有以下 9 种跳法:

1+1+1+1+1

1+1+1+2

1+1+2+1

1+2+1+1

2+1+1+1

2+1+2

1+1+3

1+3+1

3+1+1

【样例输入】

5 3 10

【样例输出】

397

这种题可以用递归的DFS解也可以用动态规划,相比较经典的递归走台阶问题,由于题目没有限定第一步跳的种类,所有导致有多种方法。递归之后也是无法求解递归无法求解的题目。因为重复计算。计算规模o(L的k次方),所以采用了动态规划+递推做的此题,我们可以建立一个2维数组dp[i][j] 。

i 表示舞台距离,j表示第一次跳j格时。 dp[i][j]表示我当前步数用j步走 可以多少种方法走到i。

p意思就是连续跳大于等于p时就会摔倒。

d[i][j]i跳数的取值范围0-K

j的取值范围是0-L

规律描述:当舞台长度为1时,我第一步为1时dp[1][1]=1 种方法 当第一步为2时 d[1][2]=0种。当第一步为3时dp[1][3]=0种。

当舞台长度为2时,我第一步为1时dp[2][1]=1种方法 当第一步为2时dp[2][2]=1种。当第一步为3时dp[2][3]=0种.

当我们得到长度为2 第一步为1时, 我当前的长度减1 剩余舞台长度为1,我们可以看到舞台为1的时候一共只有1种方法那么当长度为dp[1][1]+dp[1][2]+dp[1][3]=dp[2][1]=1 第一步为1时就是一种方法。因为当跳的步数和长度相等的时候只有一种方法 dp[2][2]=1。

如果连续两次都是跳跃,而且两次跳跃的距离都至少是 p,我们知道j是第一种跳法,k就是第2个选择的跳法所以 j>=b 分为二种转移方程,

当j>=b , 说明我们第一次跳了大于p的距离如果我们第二次在大于p那么蓝跳跳将会摔倒所以我们dp[4][2]+=dp[2][1] 不可以选择dp[2][2]和dp[2][3]

那么转移方程得:dp[i][j]+=dp[i-j][k]

当第一次小于p的长度,我们第二次就把所有可能选择上dp[4][1]=dp[3][1]+dp[3][2]+dp[3][3]

那么转移方程得:dp[i][j]+=sum(dp[i-j])。

但是这种不是最优解最多跑80%的数据。

创建一个双层的循环数组,0层存j<b的方式个数,1层存b<p+1方式个数。和上面方法差不多只不过是以双层的格式存储,这样可以少很多的计算量。

我们先把已知的数据写入二维数据中dp[1][0]=1,然后遍历2,s+1和1,p+1,因为当s=0时 方法只有一种。把dp[0][1]=1 或者dp[0][0]=1 我只是把这个当上面方法dp[i][j]+=1用了。

这个转移方程也是2个,一个 (1,b) 和(b,p+1) 把j<b 存在dp[i][0] b<p+1存在dp[i][1]。

转移方程分别为 dp[i][0]+=dp[i-j][1]+dp[i-j][0], dp[i][1]+=dp[i-j][0]。

这种就可以把数据跑完了计算量把上个方法少了很多。

每一行都要递进的缩进去四个空格,我发的时候没注意格式

for i in range(7,100,7):

for j in range(9,100 - i,9):

if (100 - i - j) % 4 == 0:

print('第一大题每道小题%d分,第二道大题每道小题%d分,第三道大题每道小题%d分' %(int(i/7),int(j/9),int((100-i-j)/4)))

from seleniumimport webdriver

import time

from selenium.webdriverimport ActionChains

driver = webdriver.Chrome()

driver.get("https://accounts.douban.com/passport/login")

# 点击密码登录

driver.find_element_by_class_name('account-tab-account').click()

# 定位账户 # 输入内容

driver.find_element_by_id('username').send_keys('2331566038')

driver.find_element_by_id('password').send_keys('*********')

# 点击登录

driver.find_element_by_link_text('登录豆瓣').click()

# 进入内嵌滑动验证页面

iframe = driver.find_element_by_id('tcaptcha_iframe')

driver.switch_to_frame(iframe)

element = driver.find_element_by_xpath('//*[@id="tcaptcha_drag_thumb"]')

ActionChains(driver).click_and_hold(on_element=element).perform()

ActionChains(driver).move_to_element_with_offset(to_element=element,xoffset=180,yoffset=0).perform()

driver.save_screenshot('豆瓣.png')

time.sleep(5)

driver.quit()

import urllib.request

import urllib.parse

url ="http://www.baidu.com/s"

word = {"wd":"浙江大学"}

word = urllib.parse.urlencode(word)

new_url = url +"?" + word

header = {

"User-Agent":"Mozilla/5.0 (Windows NT 10.0Win64x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/89.0.4389.114 Safari/537.36"

}

resquest = urllib.request.Request(new_url,headers = header,)

response = urllib.request.urlopen(resquest)

html = response.read().decode('utf-8')

print(html)