JavaScriptで有効な括弧列にするために必要な最小の追加数を求める方法
問題
今回は、'[' と ']' のみで構成される文字列 str を受け取るJavaScript関数を作成します。
この関数の目的は、結果として得られる括弧の組み合わせが有効(バランスの取れた状態)になるように、必要な最小数の角括弧('[' または ']')を任意の位置に追加することです。そして最後に、追加した括弧の最小数を返します。
例えば、関数への入力が以下の場合を考えてみましょう。
入力
const str = '[]]';
出力
const output = 1;
出力の説明
先頭に '[' を1つ追加すれば、文字列は [[]] となりバランスが取れます。したがって答えは 1 です。
アルゴリズムの考え方
この問題はスタックを使用せず、シンプルなカウンター方式で効率的に解くことができます。基本的な発想は以下の通りです。
- 変数
leftとrightを 0 で初期化します。leftは「対応する']'をまだ見つけていない'['の数」、rightは「対応する'['が存在せず余ってしまった']'の数」を追跡します。 - 文字列を先頭から順に走査し、
'['が出現したらleftをインクリメントします。 ']'が出現した場合、left > 0であれば未処理の'['とマッチさせられるのでleftをデクリメントします。マッチできる'['が存在しない場合は、その']'は余りになるためrightをインクリメントします。- 走査終了後、
left + rightを返せば、それが必要な追加括弧の最小数です。
このアプローチでは、各文字を一度だけ調べるため、時間計算量は O(n)、空間計算量は O(1) となります。
実装例
const findAdditions = (str = '') => {
let left = 0;
let right = 0;
for (let i = 0; i < str.length; i++) {
if (str[i] === '[') {
left += 1;
} else if (str[i] === ']') {
if (left > 0) {
left -= 1;
} else {
right += 1;
}
}
}
return left + right;
};
console.log(findAdditions(str));出力
1
コードのポイント
- 単一パスで完結: 文字列を一度だけ走査するため、非常に高速です。
- 追加メモリ不要: スタックや配列を使わず、2つの整数カウンターだけで済みます。
- 正確性の保証: 余った
'['の後ろに']'を、余った']'の前に'['をそれぞれ追加すれば必ず有効な文字列になるため、left + rightが理論上の最小値と一致します。
-
JavaScriptの正規表現における\dと\Dの違いを徹底解説
\dと\Dの違いとは?JavaScriptの正規表現には、\dと\Dという対になるパターンがあります。この2つはまったく逆の働きをするのが大きな特徴です。\dはテキスト内の数字(0〜9)にマッチし、\Dは数字以外の文字(アルファベット、記号、スペースなど)にマッチします。これらのパターンは、グローバル検索フラグである「g」と組み合わせて使われることが多く、これによりテキスト全体から該当するすべての文字を抽出できます。gフラグを使わない場合、最初にマッチした1文字だけが返される点に注意しましょう。書式1:\d(数字にマッチ)new RegExp(\\d, g);書式2:\D(数字以外にマッチ)n
-
JavaScriptのfindIndex()メソッドの使い方を徹底解説
JavaScriptのfindIndex()メソッドは、配列の中から条件に合致する最初の要素を見つけ、そのインデックス(添字)を返すためのメソッドです。条件を満たす要素が存在しない場合は「-1」が返されます。配列の検索処理において、要素そのものではなく「位置」を知りたい場合に非常に便利なメソッドです。findIndex()の基本構文array.findIndex(function(currentValue, index, arr), thisValue)各引数の意味は以下の通りです。currentValue:現在処理中の要素の値index:現在処理中の要素のインデックス(省略可能)arr:対象