Skip to content

Conversation

katsukii
Copy link
Owner


### 思考メモ
* 他の方のPRを見て、ループ一つにつき一文字列を走査するという固定観念に囚われていたことに気づいた
* あまり型にとらわれずに自由な発想で解き方を工夫することを学んだ

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.

以前同様のフィードバックを受けたのですが、頭から抜けていたようです。癖付けないとですね。ありがとうございます。

@Yoshiki-Iwasa
Copy link

問題文下のFollow upも考えて見るといいかもです

Follow up: Suppose there are lots of incoming s, say s1, s2, ..., sk where k >= 109, and you want to check one by one to see if t has its subsequence. In this scenario, how would you change your code?

if (sLength > tLength) return false;

for (int sIndex = 0; sIndex < sLength; sIndex++) { // traversal of s
if (s.charAt(sIndex) == t.charAt(tIndex) && sIndex == sLength - 1) return true;
Copy link

Choose a reason for hiding this comment

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

tIndex が配列外アクセスしそうですね。(そもそもこの行がいらない気がします。)

for (int sIndex = 0; sIndex < sLength; sIndex++) { // traversal of s
if (s.charAt(sIndex) == t.charAt(tIndex) && sIndex == sLength - 1) return true;
while (tIndex < tLength && s.charAt(sIndex) != t.charAt(tIndex)) { // traversal of t
if (tIndex == tLength) return false;
Copy link

Choose a reason for hiding this comment

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

ここ、上の while との関係で実行されません。while の後ろに。

Comment on lines 82 to 83
if (sLength > 0 && tLength > 0 && s.charAt(sIndex) == t.charAt(tIndex)) sIndex++;
if (tLength > 0) tIndex++;
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.

ありがとうございます。これで十分でしたね。

while (true) {
    if (sIndex == sLength) return true;
    if (tIndex == tLength) return false;
    if (s.charAt(sIndex) == t.charAt(tIndex)) sIndex++;
    tIndex++;
}

Comment on lines 100 to 101
int sLength = s.length();
int tLength = t.length();
Copy link

Choose a reason for hiding this comment

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

この変数は置かないほうがいいかもしれません。
sIndex < s.length()
のほうが意味がはっきりしていませんか。

Copy link
Owner Author

Choose a reason for hiding this comment

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

@oda
t.length()はたしかに変数化する必要はないですね。
一方で、複数回呼び出す処理(ここでは s.length() )は無思考的に変数に格納してしまっておりました。この程度のオーバーヘッドは無視していいと言われればそのとおりと思いつつ、このあたりのバランス感覚が乏しいので判断基準などあればアドバイスいただけないでしょうか。

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.

なるほど、理解しました。オーバーヘッドを過剰見積もりしていたと同時に、変数を読み手が追跡し続ける必要があるコストを考えると確かになと思いました。以後もう少し柔軟に適用していきたいと思います。

@katsukii katsukii merged commit 89f4edb into main Jan 30, 2025
@nittoco
Copy link

nittoco commented Feb 3, 2025

もしご覧になってなかったら、この辺を一通り見て、実際いろんな場合を書いてみるといいかもしれません
https://discord.com/channels/1084280443945353267/1225849404037009609/1243290893671465080

@katsukii katsukii changed the title 392. Is Subsequencecreate 392. Is Subsequence Feb 4, 2025
@katsukii
Copy link
Owner Author

katsukii commented Feb 4, 2025

@nittoco 承知しました。ありがとうございます。見てみます。

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