問題描述:
任意給定乙個正整數n,求乙個最小的整數m(m>1),使得m*n的十進位制結果只含有1和0;
問題解答:
1.窮舉法
for( m=2; ; m++)
} 一旦n較大,比如n=99,m=1122334455667789,m*n=111,111,111,111,111
2.問題轉換:
原問題可以轉化為:求乙個只含有1與0正整數,能被n整除;
觀察x的取值:1,10, 11, 100, 101, 110, 111,1000……
再引入乙個變數 j=x%n, 直接遍歷x,
通過乙個佇列儲存值和餘數j,當j出現過時,乘以10,乘以10加1,跟餘數相同的前面那個數效果一樣,所以可以不計算。
[cpp]view plain
copy
print?
#include
#include
using
namespace
std;
struct
qnode
qnode():v(0),r(0){}
};
intmain()
q.pop();
if(!bn[t.r*10 % n])
if(!bn[(t.r*10+1)%n])
} } ok:;
} return
0;
}
問題描述:
是否能從陣列中迅速找出兩個數字使得這兩個數字的和為乙個給定的數字sum。
問題解答:
1.窮舉;
o(n^2)
2.對於每個數字a[i], 查詢sum-a[i]是否在陣列中,已經變為乙個查詢問題:
可以先排序(只需一次),然後二分,o(n*logn)
或者hash對映,查詢另乙個數字是否在陣列中,time:o(1), space:o(n)
3.先排序 time:o(n*logn);(排序演算法總結)
令i=0,j=n-1,看a[i]+a[j]是否等於sum;
若大於sum,j往前移j--, 若小於sum,i往後移i++.
擴充套件問題:
1.若是「三個數字」呢?
對於「三個數字」其實就是對於陣列中的每個數字array[i]判斷陣列中的其他數字是否存在兩個數字的和為sum-array[i],以此遞迴下去。
2.若找不到滿足條件的一對數字,問怎樣找到最優解?
2. 如果找不到結果,可以儲存做差的結果,找出差值最小的解
總結:
不論原序列是有序還是無序,解決這類題有以下三種辦法: 1
、二分(若無序,先排序後二分),時間複雜度總為o(n*logn),空間複雜度為o(1); 2
、掃瞄一遍x-s[i] 對映到乙個陣列或構造hash表,時間複雜度為o(n),空間複雜度為o(n); 3
、兩個指標兩端掃瞄(若無序,先排序後掃瞄),時間複雜度最後為:有序o(n),無序o(n*logn+n)=o(n*logn),空間複雜度都為o(1)。所以,要想達到時間o(n),空間o(1)的目標,除非原陣列是有序的(指標掃瞄法),不然,當陣列無序的話,就只能先排序,後指標掃瞄法或二分(時間n*logn,空間o(1)),或對映或hash(時間o(n),空間o(n))。時間或空間,必須犧牲乙個,自個權衡吧。
綜上,若是陣列
有序的情況下,優先考慮兩個指標兩端掃瞄法,以達到最佳的時(o(
n)),空(o(
1))效應。否則,如果要排序的話,時間複雜度最快當然是只能達到
n*logn
,空間o(1
).
每日一題 整數劃分
title 每日一題 整數劃分 date 2019 10 27 17 15 16 tags 91.整數劃分 15分 c時間限制 2 毫秒 c記憶體限制 65535 kb 題目內容 對於乙個正整數n的劃分,就是把n變成一系列正整數之和的表示式。注意,分劃與順序無關,例如6 5 1跟6 1 5是同一種分...
每日一題力扣14
編寫乙個函式來查詢字串陣列中的最長公共字首。如果不存在公共字首,返回空字串 class solution def longestcommonprefix self,strs list str str ifnot strs return count len strs 陣列的長度,即其中有多少個字串 p...
如何寫出乙個符合要求的正則
如果你正在苦惱如何寫乙個正則的話,那麼或許本文對你有所幫助 文中的這個例子或許同個字串擷取同樣可以做到,但本文僅嘗試以純正則的角度解決問題 首先看一下這個例子 d mj 1989 d mj 2000 d 17.05.2011 mj 2013 d mj 2010 01.11.2010 d 24.06....