Python

 Computer >> コンピューター >  >> プログラミング >> Python
  1. Pythonで値kに基づいて連結リストのノードを並べ替えるプログラム

    単方向連結リストとある値 k が与えられたとします。このとき、ノードを次の順序で並べ替える必要があります。まず値が k より小さいノードを先頭に集め、次に値が k と等しいノードを続け、最後にそれ以外(k より大きい)ノードを末尾に配置します。重要な制約として、ノード同士の相対的な順序は元のまま維持しなければなりません。例えば、入力が L = [4, 3, 6, 6, 6, 10, 8]、k = 6 の場合、出力は [4, 3, 6, 6, 6, 10, 8] となります。4 と 3 は 6 未満なので先頭に、6 は 6 と等しいので中間に、10 と 8 は 6 より大きいため末尾に配置されま

  2. 【Python】連結リストをジグザグ二分木に変換するプログラムの書き方

    問題の概要単方向連結リスト(片方向リンクリスト)が与えられたとき、次のルールに従って二分木へ変換することを考えます。連結リストの先頭ノード(head)が、二分木のルートになります。それ以降の各ノードは、その値が親ノードより小さい場合は左の子に、そうでない場合は右の子になります。たとえば、入力が [2,1,3,4,0,5] の場合、変換後の二分木は次のような「ジグザグ」形状になります。解き方の手順この問題は、再帰的に呼び出す関数 solve() を定義すると、シンプルに解くことができます。具体的な手順は以下の通りです。ノードを引数として受け取る関数 solve() を定義します。ノードが nul

  3. Pythonで2つのソート済みリンクリストの和集合(結合)を求めるプログラム

    2つのソート済み連結リスト L1 と L2 が与えられたとします。このとき、両方のリストの和集合(ユニオン)に相当する、新しいソート済み連結リストを作成して返す必要があります。例えば、入力が以下のような場合を考えてみましょう。L1 = [10, 20, 30, 40, 50, 60, 70]L2 = [10, 30, 50, 80, 90]この場合、出力は重複を除いた [10, 20, 30, 40, 50, 60, 70, 80, 90] となります。解法のアプローチこの問題は、再帰を使って両リストの先頭要素を比較しながら処理を進めることで解決できます。手順は以下の通りです。関数 solve

  4. Pythonで最大1組の文字を入れ替えた後に得られる最長の連続する「1」を見つける方法

    問題概要 0と1だけで構成される2進文字列 s が与えられます。文字列の中で最大1組の文字を入れ替えることができるとき、その操作によって得られる最も長い連続した「1」の部分文字列の長さを求めるのが目標です。 たとえば、入力が s = 1111011111 の場合、出力は 9 になります。s[4] の「0」と s[9] の「1」を入れ替えることで、「1」が9個連続する並びを作れるためです。 解法の考え方:スライディングウィンドウ この問題はスライディングウィンドウ(尺取り法)を使うことで、線形時間で効率的に解くことができます。 基本となるアイデアは次のとおりです。 ウィンドウ内に含まれる「0

  5. Pythonでリストから最長のフィボナッチ部分列の長さを求める方法

    問題の概要厳密に増加している正の整数からなるリスト nums が与えられたとします。このとき、すべての i > 1 に対して A[i] = A[i - 1] + A[i - 2] という関係(つまりフィボナッチ数列と同じ漸化式)を満たす、最も長い部分列 A(最小長は3)を見つけ、その長さを求めるのが課題です。例えば、入力が nums = [1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14] の場合、[1, 2, 3, 5, 8, 13] という部分列を選ぶことができるため、出力は 6 となります。解決のための手順この問題は、ペアごとにフィボナッチ

  6. Pythonで重なる区間をマージし、最長の区間の長さを求めるプログラム

    問題の概要それぞれ [start, end] の形式で表される区間(インターバル)のリストが与えられているとします。この課題では、重なり合う区間をいくつでもマージ(統合)して作ることができる「最も長い区間」の長さを求めます。例えば、入力が [[1, 6], [4, 9], [5, 6], [11, 14], [16, 20]] の場合を考えてみましょう。[1, 6]、[4, 9]、[5, 6] は互いに重なっているため、これらをマージすると長さ9の区間 [1, 9] が得られます。したがって、出力は 9 となります。解法のアルゴリズムこの問題は、以下の手順で効率よく解くことができます。区間のリ

  7. Pythonで数値リストから最長の符号交互部分列の長さを求めるプログラム

    問題の概要 数値リスト nums が与えられたとき、隣り合う要素ごとに符号が入れ替わる(正と負が交互に出現する)最長の部分列の長さを求めます。 例えば、nums = [1, 3, -6, 4, -3] の場合、[1, -6, 4, -3] を選ぶと符号が交互に入れ替わっているため、出力は 4 になります。 アルゴリズムの考え方 この問題は、動的計画法の考え方を用いることで O(n) の計算量で効率的に解くことができます。ポイントは次の 2 つの変数です。 pos:「正の数で終わる符号交互部分列」の最大長を保持する neg:「負の数で終わる符号交互部分列」の最大長を保持する 具体的な手順

  8. Pythonで「厳密に増加してから減少する」最長部分リスト(山型)の長さを求める方法

    問題概要数値のリスト nums が与えられます。この中から、値が厳密に増加した後に厳密に減少する(山型の形状、最小長3)最長の部分リストの長さを求めます。例えば、入力が nums = [8, 2, 4, 6, 3, 1] の場合、部分リスト [2, 4, 6, 3, 1] が厳密に増加してから減少しているため、出力は 5 となります。アルゴリズムの考え方この問題は、リストを先頭から走査しながら、増加区間と減少区間の長さをそれぞれ記録することで解決できます。手順は以下の通りです。i := 0、n := リストaのサイズ、res := 負の無限大 で初期化します。i < n - 2 の間、次

  9. Pythonで最大k個の0を反転して最長の連続する1の長さを求めるプログラム

    0と1のみで構成されるバイナリリストと、整数kが与えられたとします。最大k個の0を1に変更できるとき、すべてが1で構成される最も長い連続区間(部分リスト)の長さを求めるのがこの問題です。例えば、入力が nums = [0, 1, 1, 0, 0, 1, 1]、k = 2 の場合、出力は 6 になります。中央にある2つの0を1に変更すれば、リストは [0, 1, 1, 1, 1, 1, 1] となり、連続する6つの1が得られるためです。解決アプローチ:スライディングウィンドウ法この問題は「スライディングウィンドウ(尺取り法)」と呼ばれる手法を使うことで、O(n)の計算量で効率的に解くことができま

  10. Pythonで最大値と最小値の差がk以下となる最長の部分リストの長さを求めるプログラム

    数値のリスト nums と整数 k が与えられたとき、「リスト内の最大要素と最小要素の絶対差が k 以下」という条件を満たす、最も長い連続した部分リストの長さを求めることを考えます。 たとえば、入力が nums = [2, 4, 6, 10]、k = 4 の場合、出力は 3 になります。[2, 4, 6] を選べば、最大値 6 と最小値 2 の差がちょうど 4 となり、条件を満たすからです。 解き方のアプローチ この問題は、スライディングウィンドウと単調な両端キュー(deque)を組み合わせることで効率的に解けます。ウィンドウの右端を拡張しながら、ウィンドウ内の最大値と最小値をそれぞれ専用の

  11. Pythonで各文字がk回以上出現する最長部分文字列の長さを求める方法

    問題の概要ソート済みの文字列 s と整数 k が与えられます。このとき、「すべての文字が少なくとも k 回以上出現する」という条件を満たす最長の部分文字列の長さを求めるのが目的です。例えば、入力が s = aabccddeeffghij、k = 2 の場合を考えてみましょう。このとき最も長い条件を満たす部分文字列は ccddeeff であり、c・d・e・f の各文字がそれぞれ2回ずつ出現しています。したがって、答えは 8 となります。アルゴリズムの考え方この問題は分割統治法を使うことで効率的に解けます。基本的なアイデアは次のとおりです。まず Counter を使って文字列全体の各文字の出現回数

  12. Pythonで「Look-and-Say(見て言って)」数列のn番目の項を求める方法

    整数 n が与えられたとき、「Look-and-Say(見て言って)」数列の n 番目の項を生成するプログラムを作成します。この数列は、直前の項を読み上げるようにして次の項を作っていく特徴的な数列です。最初のいくつかの項は以下のようになります。111211211111221読み方のルール各項は、前の項を「数字の連続する個数 + その数字」という形式で読み上げることで生成されます。1(イチ)11(1が1つ)→ 前の項「1」を読んで「1が1つ」21(1が2つ)→ 前の項「11」を読んで「1が2つ」1211(2が1つ、1が1つ)→ 前の項「21」を読んで「2が1つ、1が1つ」111221(1が1つ、

  13. Pythonのネストされたリストにおける重み付き合計 II(ボトムアップの重み付け)

    問題概要 ネストされた整数のリストが与えられ、すべての整数を深さに基づく重みで掛けた合計を返すことを考えます。各要素は整数、またはリストであり、リストの要素にも整数や別のリストが含まれ得ます。 前回の問題では重みがルートから葉に向かって増加していましたが、今回は逆に下から上へ(ボトムアップ)重みが定義されます。つまり、最も深いレベル(葉)の整数の重みは 1 となり、ルートに近いレベルの整数ほど大きな重みを持ちます。 たとえば、入力が [[1,1],2,[1,1]] の場合、出力は 8 になります。これは、最深部にある 4 つの「1」が重み 1、その外側にある「2」が重み 2 となるためです(4

  14. Pythonでターゲット値より大きいペアの最小合計を求める方法(二分探索・双方向ポインタ活用)

    数値のリスト nums とターゲット値 target が与えられたとき、ターゲットより大きくなるペアの合計の中で最小のものを見つける問題を考えてみましょう。 例えば、入力が nums = [2, 4, 6, 10, 14]、target = 10 の場合、出力は 12 になります。これは、2 と 10 を選んだときの合計が 12 となり、ターゲット(10)を超えるペアの中で最も小さい合計だからです。 解法のアプローチ:双方向ポインタ(Two Pointers) この問題は、リストをソートした上で「双方向ポインタ」というテクニックを使うと効率的に解けます。手順は以下の通りです。 リスト num

  15. Pythonで多数決により過半数の票を獲得した候補者のIDを見つける方法

    本記事では、Pythonを使って多数決(過半数)を獲得した候補者のIDを見つけるプログラムを解説します。 問題の概要 n個の値を含む数値リスト nums があるとします。各数値は候補者への1票を表しています。この中から、floor(n/2) より多くの票を獲得した候補者のIDを見つけます。もし過半数の票を獲得した候補者が存在しない場合は、-1 を返します。 例えば、入力が nums = [6, 6, 2, 2, 3, 3, 3, 3, 3] の場合を考えてみましょう。リストの長さは9なので、過半数となるには5票以上が必要です。数値「3」は5回出現しているため、出力は 3 となります。 解

  16. Pythonで指定した金額を作るコインの組み合わせ数を求めるプログラム

    コインの種類を表すリストと、目標となる金額(amount)が与えられたとき、合計がちょうどその金額になる組み合わせが何通りあるかを求める問題を考えてみましょう。答えが非常に大きくなる場合は、結果を 10^9 + 7 で割った余りを返します。 たとえば、coins = [2, 5]、amount = 10 という入力の場合、出力は 2 になります。これは次の2通りの組み合わせで 10 を作れるためです。 [2, 2, 2, 2, 2] [5, 5] 解法のアプローチ:動的計画法(DP) この問題は動的計画法を使うことで効率的に解けます。dp[i] を「i 円を作る組み合わせの数」と定義し、コ

  17. Pythonで各セルに最も近い0までのマンハッタン距離を格納した行列を生成するプログラム

    問題の概要 0と1だけで構成される2値行列を考えます。この行列と同じサイズの新しい行列を作成してください。ただし、新しい行列の各セルには、元の行列においてその位置から最も近い0までのマンハッタン距離を格納します。なお、元の行列には少なくとも1つの0が存在すると仮定できます。 たとえば、入力が次のような行列だった場合を考えてみましょう。 101101110 このとき、出力は次のようになります。 101101210 これは、左下のセルだけが最も近い0までの距離が2になるためです。 解決のための手順 この問題は、動的計画法(DP)の考え方を応用し、行列を2回走査するだけで効率的に解くことができます。

  18. Pythonでソート済み行列からn番目に小さい数を見つける方法

    問題の概要 行と列がそれぞれ非減少順(昇順)にソートされた2次元行列が与えられたとき、その中からn番目に小さい数を見つけることを考えます。 例えば、次のような行列が入力されたとします。 243034316632 このとき n = 4 とすると、出力は 6 になります。 解法のアプローチ 最もシンプルで分かりやすい方法は、行列内のすべての要素を1つのリストに集め、ソートしてからn番目の要素を取り出すことです。手順は以下の通りです。 空のリスト lst を用意する 行列の各行 i について、その中の各要素 j を lst の末尾に追加していく リスト lst をソートする lst[n] を返す

  19. Pythonで行と列がソートされた2次元行列からターゲット値を検索するプログラム

    各行および各列が非降順(昇順)にソートされた2次元行列があるとします。このとき、指定されたターゲット値がその行列の中に存在するかどうかを判定する問題です。問題の例例えば、以下のような行列が与えられたとします。243034316632ここでターゲット値が 31 の場合、行列内に存在するため、出力は True となります。解法のアプローチこの問題は、行列の右上隅から探索を開始する「階段探索(スティンケースサーチ)」と呼ばれる手法で効率的に解くことができます。手順は以下の通りです。探索開始位置の列インデックス col を「列数 − 1」(つまり右端の列)に設定します。行インデックス i を 0 から

  20. Pythonで数値を削除して最大の加算スコアを求めるプログラム|区間DPによる解法

    問題の概要 数値のリスト nums が与えられます。次のような操作を考えます。 リストの先頭と末尾以外から数値を1つ選び、取り除きます。 その際、「選んだ数値 + 両隣の数値」の合計がスコアに加算されます。 この操作は、先頭と末尾を選ばない限り何度でも繰り返せます。 このとき、最終的に得られるスコアの最大値を求めるのが目的です。 入力例と動作の確認 入力が nums = [2, 3, 4, 5, 6] の場合、出力は 39 になります。手順は以下の通りです。 5 を選択:スコアは (4 + 5 + 6) = 15、配列は [2, 3, 4, 6] になります。 4 を選択:スコアは (

Total 8994 -コンピューター  FirstPage PreviousPage NextPage LastPage CurrentPage:190/450  20-コンピューター/Page Goto:1 184 185 186 187 188 189 190 191 192 193 194 195 196