問題描述:
序列中任意個連續的元素組成的子串行成為該序列的子串。現在給你乙個序列p和乙個整數k,詢問元素和是k的倍數的子串的最大長度。比如序列[1,2,3,4,5],給定的k為5,其中滿足條件的串子串為[5],[2,3],[1,2,3,4,5].所以答案是5
輸入描述:
第一行乙個整數n (1<=n<=10^5)
第二行n個整數的序列p(1<=pi<=10^5)
第三行含乙個整數k(1<=k<=10^5)
輸出描述:
輸出乙個ans,表示答案
分析思路:
本人用的是python,剛開始想用暴力求解,但看資料o(n^2),必然wa,所以想用動態規劃加二分求解,但還是掛了。後來想到了將動態規劃降維的方法,即轉化為利用sum[i]-sum[j]=t*k求i,j的最大距離。將p字首加乙個[0],便於統一下標。先遍歷一遍p,從乙個逐個相加,結果每個p[i]代表前p[:i+1]的和,每求一次,對t=p[i]%k。這裡用乙個r陣列,存在餘數對應位置存該餘數出現的下標(這裡有點拗口,即利用了r的下標即代表乙個餘數,這裡就相當於降維了)。然後再定義乙個陣列ans,用於儲存間隔值。下標即余數值,最終指出現p中的每項取餘得到的相同餘數的間隔最大值,儲存在相應餘數所對的下標中。現在回到r陣列,至於r陣列怎麼跟ans何用呢?就是取餘之後進行判斷,如果r之前沒存這個餘數,說明這個餘數第一次出現,存下下標(此處下標指的是遍歷p的下標)。如果不是第一次出現,則計算距離第一次下標的值,並比較ans中相應餘數對應的下標的ans值取大值。依次類推,然後最終求最大值。即答案。整個過程只需在遍歷p求和的過程中即可完成,時間複雜度為o(n)。這裡利用r和ans兩個陣列以及餘數與下標相等的巧妙性將二維降成了一維。
ps:這裡餘數對應的下標,即余數值與下標值相等。
**實現:
#-*-coding:utf-8 -*-
while true:
try:
n=int(raw_input())
res=map(int,raw_input().split())
k=int(raw_input())
res=[0]+res
r=[-1 for i in range(n+1)]
ans=[-1 for i in range(n+1)]
r[0]=0
for i in range(1,n+1):
res[i]+=res[i-1]
t=res[i]%k
if r[t]!=-1:
m=i-r[t]
ans[t] = max(m, ans[t])
else:
r[t]=i
print max(0,max(ans))
except:
break
9 6 美團筆試程式設計題
a 題意 求一棵樹中,從點1遍歷所有點的最短距離,所有相鄰點之間的距離都是1 思路 假設問題是這樣,從點1遍歷所有點最後回到點1,很顯然對於結果就是2 n 1 因為每條邊都會遍歷恰好兩次,n是結點數目.那麼此時只需要遍歷所有點,不需要回到點1,那麼我們可以選擇一條從1出發的最長路徑,這條路徑中的邊只...
2017美團秋招筆試程式設計題 後台研發
1 求所有能被7整除的數字 分析 方法一 採用暴力解法,即兩兩數字都組合一遍對7取餘判斷的方法,演算法複雜度o n2 會超時,提交成功率為70 方法二 求乙個數a前面拼接上什麼數能夠被7整除,只需進行以下操作即可 數a前面依次拼上0 6,變為0a,1a,2a 6a。依次判斷這7個數能否被7整除 以1...
美團點評2017秋招筆試程式設計題 題解
昨晚臨時做了下美團2017年的校招題 純屬無聊 感覺美團的題就做得很舒服了,考想法,量小,只要你的idea夠好,就幾行,學習了!大富翁遊戲,玩家根據骰子的點數決定走的步數,即骰子點數為1時可以走一步,點數為2時可以走兩步,點數為n時可以走n步。求玩家走到第n步 n 骰子最大點數且是方法的唯一入參 時...