From cae26bad97127d7e6f1dd2d41e83c7b25b25c2cb Mon Sep 17 00:00:00 2001 From: potrue <126231160+potrue@users.noreply.github.com> Date: Mon, 25 Aug 2025 23:02:25 +0900 Subject: [PATCH 1/2] 392. Is Subsequence https://leetcode.com/problems/is-subsequence/description/ --- 392/392.md | 65 ++++++++++++++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 65 insertions(+) create mode 100644 392/392.md diff --git a/392/392.md b/392/392.md new file mode 100644 index 0000000..f16b88b --- /dev/null +++ b/392/392.md @@ -0,0 +1,65 @@ +## 何も見ずに解いてみる + +```cpp +class Solution { +public: + bool isSubsequence(string s, string t) { + auto it = s.begin(); + for (char c : t) { + if (c == *it) { + ++it; + } + if (it == s.end()) { + break; + } + } + return it == s.end(); + } +}; +``` + +## 他の人のコードを見てみる + +https://github.com/tokuhirat/LeetCode/pull/57/files +https://github.com/KentaroJay/Leetcode/pull/9/files +https://github.com/ryosuketc/leetcode_arai60/pull/57/files +for文で回すとsが終わりまで到達したときにわざわざif文を入れてbreakしなければならなくなるのがいやだなと思っていたので、この書き方は結構いいと思った。 +https://github.com/Ryotaro25/leetcode_first60/pull/62/files +https://github.com/usatie/leetcode/pull/5/files + +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? + +tにおいてある文字が出てくるindexの配列を>の辞書として管理しておいて、現在の場所以降で一番最初にあるs中の文字が出てくる場所を二分探索で探す方法(1つのsあたりの時間計算量O(|s|log|s|))の他に、 +この問題のように文字の種類が固定されている(26種類だけ)の場合は、tにおけるすべてのindexにおいて次にある文字が出てくるindexが書いてある配列を最初に構成してしまうことで、計算量がo(|s|)にすることもできる。(ただしその配列の構成にO(|t| × 文字の種類)の時間とメモリがかかるので大体のユースケースで見合ってなさそう) + +変数名にit_tという名前を使おうとしたらleetcodeのエディター上で名前が水色になるのでなんだろうと思って調べてみたら、intまたはuintで始まって_tで終わるような名前はC++の予約語で、_tで終わるだけのものもPOSIX(Unix系のOSの国際標準?)では予約されているらしい。 +少なくともPOSIXライブラリをincludeするようなときは避けたほうが良さそう? + +https://stackoverflow.com/questions/56935852/does-the-iso-9899-standard-has-reserved-any-use-of-the-t-suffix-for-identifiers +https://www.iso-9899.info/n1570.html#7.31.10 + +C++の標準規格はドラフト版が無料で公開されているらしいが正式版は有料らしい。 +image +というか、3年おきの更新だったのか。これも知らなかった。 + +## 最終コード + +```cpp +class Solution { +public: + bool isSubsequence(string& s, string& t) { + auto s_it = s.begin(); + auto t_it = t.begin(); + while (s_it != s.end() && t_it != t.end()) { + if (*s_it == *t_it) { + ++s_it; + } + ++t_it; + } + return s_it == s.end(); + } +}; +``` + +イテレーターで書くよりintとかsize_tでインデックスを保存してoperator[]で要素比較したほうが読みやすいですかね? From 909754ea9d7e485a7eecad9644020a58ed42588f Mon Sep 17 00:00:00 2001 From: potrue <126231160+potrue@users.noreply.github.com> Date: Tue, 26 Aug 2025 02:50:45 +0900 Subject: [PATCH 2/2] Update 392.md --- 392/392.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/392/392.md b/392/392.md index f16b88b..12eda9f 100644 --- a/392/392.md +++ b/392/392.md @@ -31,7 +31,7 @@ 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? tにおいてある文字が出てくるindexの配列を>の辞書として管理しておいて、現在の場所以降で一番最初にあるs中の文字が出てくる場所を二分探索で探す方法(1つのsあたりの時間計算量O(|s|log|s|))の他に、 -この問題のように文字の種類が固定されている(26種類だけ)の場合は、tにおけるすべてのindexにおいて次にある文字が出てくるindexが書いてある配列を最初に構成してしまうことで、計算量がo(|s|)にすることもできる。(ただしその配列の構成にO(|t| × 文字の種類)の時間とメモリがかかるので大体のユースケースで見合ってなさそう) +この問題のように文字の種類が固定されている(26種類だけ)の場合は、tにおけるすべてのindexにおいて次にある文字が出てくるindexが書いてある配列を最初に構成してしまうことで、1つのsあたりの計算量をo(|s|)にすることもできる。(ただしその配列の構成にO(|t| × 文字の種類)の時間とメモリがかかるので大体のユースケースで見合ってなさそうな気はする) 変数名にit_tという名前を使おうとしたらleetcodeのエディター上で名前が水色になるのでなんだろうと思って調べてみたら、intまたはuintで始まって_tで終わるような名前はC++の予約語で、_tで終わるだけのものもPOSIX(Unix系のOSの国際標準?)では予約されているらしい。 少なくともPOSIXライブラリをincludeするようなときは避けたほうが良さそう?