0.試合後のまとめ
たった2つの質問があった別の日でした。残念ながら、私の心は疲れ果てていましたが、幸いなことに、結果はほとんど気が進まなかったので、恥ずかしくないでしょう...
1.トピック1
質問1に与えられた質問へのリンクは次のとおりです。
1.問題解決のアイデア
この質問については何も言うことはありませんが、質問の意味によれば、各山のピーク高さは前のすべての要素の合計であるため、累積後の最大値を見つけることができます。
2.コードの実装
Pythonコードは次のとおりです。
class Solution:
def largestAltitude(self, gain: List[int]) -> int:
return max(0, max(accumulate(gain)))
評価のためにコードを送信した後、32ミリ秒かかり、14.1MBのメモリを消費しました。
2.トピック2
トピック2のテスト問題へのリンクは次のとおりです。
1.問題解決のアイデア
この質問は、コンテスト中にはまったく完了しませんでした。コンテスト後、他の人の解決策を見て、彼らのアイデアは非常に単純でわかりやすいため、3つの見解にショックを受けましたが、このアイデアは不完全であり、バグになる...…
いずれにせよ、ここではまず問題解決のアイデアを説明し、次にコードの実装を説明します。とにかく、読者は自分でそれについて考えることもできます。個人的には、このソリューションには論理的な抜け穴があるといつも思っています...
彼らのアルゴリズムのアイデアの核心は次のとおりです。
- 特定の言語LANを調査します。2人がコミュニケーションできない場合は、両方がその言語を学習し(そうでない場合)、その言語でコミュニケーションをとることができます。すべての言語をトラバースすると、最も少ない回数で教える必要がある結果が最終的な答えになります。
ただし、ここには非常に奇妙な論理があります。つまり、すべての人に同じ言語を教えることが最適な解決策でなければならないのはなぜですか。なぜ彼らの中には言語Aを教え、他の人々に言語Bを教えることが不可能なのですか?
とにかく、最初に上記のアイデアに従ってコードを記述し、すべてのテスト例に合格できることを確認します。
2.コードの実装
Pythonコードは次のとおりです。
class Solution:
def minimumTeachings(self, n: int, languages: List[List[int]], friendships: List[List[int]]) -> int:
languages = [set(langs) for langs in languages]
res = len(friendships)
for lan in range(n):
teach = set()
for u, v in friendships:
u, v = u-1, v-1
if languages[u] & languages[v]:
continue
if lan not in languages[u]:
teach.add(u)
if lan not in languages[v]:
teach.add(v)
res = min(res, len(teach))
return res
コード評価を送信して取得:8408ms、27.8MBのメモリを占有。
3.トピック3
トピック3のテスト問題へのリンクは次のとおりです。
1.問題解決のアイデア
この質問は質問3に配置されましたが、実際には2番目の質問よりもはるかに単純に感じます。
エンコードされたの各要素についてy[i] = x[i] ^ x[i+1]
、基本的な性質によりx ^ x == 0
、指定された配列に排他的論理和演算を累積することで新しい配列を取得できますz[i] = x[0] ^ x[i+1]
。それらの要素はそれぞれです。
残りの質問は、それをどのように見つけるかx[0]
です。要素の総数がベースであるため、XOR演算によってすべての偶数の要素を取得できます。次にx[0]
、要素が来る以外のすべての要素のXOR結果を取得できます。1からnまで、つまり次のようになります。
x[0] = 1^2^...^n ^ z[1]^z[3]^...
これから、解を逆にしてすべての数値を取得できます。
2.コードの実装
Pythonコードは次のとおりです。
class Solution:
def decode(self, encoded: List[int]) -> List[int]:
n = len(encoded)
x1 = 0
for i in range(1, n+2):
x1 = x1 ^ i
# print(x1)
for i in range(1, n, 2):
x1 = x1 ^ encoded[i]
# print(x1)
s = deepcopy(encoded)
for i in range(n-1):
s[i+1] = s[i] ^ s[i+1]
res = [x1] + [x1 ^ x for x in s]
return res
評価のためにコードを送信して取得します。1492msかかり、35MBのメモリを消費します。
4.トピック4
質問4のテスト問題へのリンクは次のとおりです。
1.問題解決のアイデア
競技中、動的計画法を使用して問題を解決することを考えました。コードは簡単に記述できましたが、予期せずタイムアウトの問題が発生し、ハングアップしました。
ゲーム終了後、他の人の解決策を見ましたが、実際、ゲーム中に彼らのアイデアについて考えました。
- 取得する製品番号を因数分解して、その因数を取得します。
- 因数分解の結果に応じて分析解を行います。
ただ、当時は2点目の実現を考えていなかったので、他の人の答えを読んで理解できたので、理解してみるととてもシンプルな感じがします。
私たちは、特定のクエリに対して調べる(n, k)
としよう頁pはkの因数であり、pppの次数はmmですm、つまりk % p**m == 0 and k % (p**(m+1)) != 0
。
現時点では、このmmにする必要がありますm thpppからnnn個の数のうち、1つの数に複数を使用できます。セグメンテーション問題と同等の、我々は今持っているミリメートルをn − 1n-1を挿入する必要があるm個の同一要素n−nnに分割された1つのグリルnコピー、いくつの異なる挿入方法があります。
この質問には、基本的に次のように数秒で答えることができます。Cn + m − 1 n − 1 C_ {n + m-1} ^ {n-1}Cn + m − 1N - 1。
さまざまな要因について、それらの配置は互いに独立しているため、すべての要因のソリューションを統合することで最終結果を得ることができます。
2.コードの実装
Pythonコードは次のとおりです。
class Solution:
def get_prime_number(self):
return [2, 3, 5, 7, 11, 13, 17, 19, 23, 29, 31, 37, 41, 43, 47, 53, 59, 61, 67, 71, 73, 79, 83, 89, 97, 101, 103]
@lru_cache(None)
def C(self, n, m):
MOD = 10**9 + 7
res = 1
if m < n // 2:
m = n - m
for i in range(m+1, n+1):
res *= i
for i in range(n-m):
res = res // (i+1)
return res % MOD
def waysToFillArray(self, queries: List[List[int]]) -> List[int]:
MOD = 10 ** 9 + 7
primes = self.get_prime_number()
def f(n, k):
if n == 1:
return 1
elif k == 1:
return 1
factor = defaultdict(int)
res = 1
for p in primes:
while k % p == 0:
factor[p] += 1
k = k // p
res *= self.C(n-1+factor[p], n-1)
if k != 1:
res *= n
return res % MOD
return [f(n, k) for n, k in queries]
評価のためにコードを送信した後、864ミリ秒かかり、32.1MBのメモリを消費しました。現在の最適なコード実装について。