Skip to content

Conversation

@Kaichi-Irie
Copy link
Owner

問題へのリンク

House Robber II - LeetCode

言語

Python

問題の概要

この問題は、円形の家のリストが与えられたときに、隣接する家を盗むことができない条件の下で、最大の金額を盗む方法を見つけることです。
家が一列に並んでいる場合の最大金額を求める問題House Robber - LeetCodeと似ていますが、円形の配置により、最初と最後の家は隣接しています。つまり、最初の家と最後の家の両方を盗むことはできないという制約が追加されています。

自分の解法

以下の二つの場合に分けて考えます。円形の制約から、求める答えは以下の二つのケースのうちいずれかになります。

  1. 最初の家を盗まない場合(最後の家は盗んでもよい)
  2. 最後の家を盗まない場合(最初の家は盗んでもよい)

そして、それぞれのケースに対して、通常の「House Robber」の問題を動的計画法で解くことで、最大金額を求めます。動的計画法の際には、二つの変数の値だけを逐次更新していくことで、空間計算量をO(1)に抑えます。

  • 時間計算量:O(len(nums))
  • 空間計算量:O(1)

step2

  • rob_houses_linearをprivateな関数_rob_houses_linearに変更しました
  • 変数の更新の際に使う変数tmpprev_tmpに変更しました
    • tmpという変数が一般に良くないというのはわかりつつも、このような一時的に値を保持して数行以内で使われるような変数ではむしろわかりやすいのでは無いかと思っています。

step3

  • dpの漸化式をコメントに書きました
    • dp[i] = max(dp[i-1], dp[i-2] + nums[i])
    • dp[i]i番目の家まで考えたときの最大金額を表します。

次に解く問題の予告



## step3
- dpの漸化式をコメントに書きました
Copy link

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

単に dp で、dynamic programming だとはあまり通じない気がします。
たとえば、Chrome のソースコードで dp で調べた結果です。
https://source.chromium.org/search?q=%5Cbdp%5Cb&sq=

あと、最近の LLM、プロダクションのコードにしてくれと頼むときれいにしてくれます。

Copy link
Owner Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

レビューありがとうございます。
dp は余り浸透していない、いわば競プロの方言なのですね、気をつけます。

プロダクションのコードにしてくれと頼む

いつもLLMにコードレビューは頼んでいたのですが、その指示の出し方はしたこと無かったので参考になります。ありがとうございます。

def rob(self, nums: list[int]) -> int:
if not nums:
return 0
elif len(nums) == 1:
Copy link

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

直前に return 0 があるため、 if 文にしてしまってもよいと思います。

Copy link
Owner Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

レビューありがとうございます。
そうですね、early return したときに以降のif文を if にするのか elifにするのか、いつも少し迷っているのですが、 if の方がわかりやすいのならそちらに統一しようと思います。

elif len(nums) == 1:
return nums[0]

max_rob_amount_excluding_first = self.rob_houses_linear(nums[1:])
Copy link

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

スライスでコピーが作られるという余分な処理を避けるため、個人的にはリストと開始・終了インデックスを補助関数に渡したいです。

Copy link
Owner Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

たしかにおっしゃる通りですね。心がけていきます。

@Kaichi-Irie Kaichi-Irie changed the title Solve 213_house_robber_ii_medium 213 house robber ii medium Sep 10, 2025
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

4 participants