forループの実行回数を返す

生田 陸人
LuaGate エンジニア / 現役エンジニア
編集 LuaGate編集部

forループの実行回数を返す

このレッスンで分かること

  • O(1) は一定、O(n) は比例、O(log n) は半分ずつ縮める、O(n^2) は 2 乗で増える
  • Python の range(n)0, 1, 2, ..., n-1 まで合計 n 個の値を返します
  • プログラムが速いか遅いかを語るとき、for ループが 何回まわるか が最重要の指標になります

forループの実行回数を返す とは

for ループを n 回まわすときに、本当に n 回実行されているのかを自分の手で数え、計算量の感覚を掴む。

プログラムが速いか遅いかを語るとき、for ループが 何回まわるか が最重要の指標になります。本章ではアルゴリズムの効率を測る尺度として Big-O (オーダー記法) を扱いますが、その入口として、まずは「ループが本当に n 回実行されているか」を自分で数えてみましょう。

本レッスンの課題は、整数 n を受け取り、for i in range(n): のようなループを実行したとき、ループ本体が 何回実行されたか をカウントして返す関数を書くことです。当たり前のように見えますが、n = 0n = 1 の挙動、ループ変数の範囲をきちんと理解しているかが試されます。

ループ回数 = アルゴリズムの 実行時間の素 。まずは「1 重ループは O(n)」という感覚を体に染み込ませよう。

range の挙動を正しく理解する

Python の range(n)0, 1, 2, ..., n-1 まで合計 n 個の値を返します。JavaScript で for (let i = 0; i < n; i++) と書いたときと同じ範囲です。つまり n = 5 なら 5 回、n = 0 なら 0 回まわります。これを正確に把握することが、計算量の議論の 大前提 です。

diagram (will load when visible)

図のポイント (テキスト併記)

  • 図のとおり、ループ本体は i = 0 から i = n-1 まで n 回呼ばれます

図のとおり、ループ本体は i = 0 から i = n-1 まで n 回呼ばれます。終了時のカウンタは n になります。

O(n) の意味

計算量の表記 O(n) は「入力 n に比例した時間がかかる」ことを意味します。つまり n10 倍になると、おおむね処理時間も 10 倍になります。1 重の for ループは典型的な O(n) の処理です。

O(n) は「n に比例」。O(1) は「n に関係なく一定」。この 2 つの違いがすべての出発点。

Python での実装例

Python

def countIterations(n): count = 0 for i in range(n): count += 1 return count

素直に count0 から始めて、ループの中で += 1 するだけです。n0 以下なら range が空になるので、count0 のままになります。

JavaScript での実装例

JavaScript

function countIterations(n) { let count = 0; for (let i = 0; i < n; i++) { count += 1; } return count; }

i < n の条件式が大事で、i <= n と書いてしまうと 1 回多くまわってしまうバグの典型例になります。

よくある間違い

1 つ目は オフバイワン エラー (off-by-one) です。i <= ni < n + 1 などと書いてしまい、n + 1 回実行されてしまうケースが頻発します。range(n)i < n は厳密に n 回まわると覚えましょう。

2 つ目は 負の nn = 0 を考慮しないケースです。n = 0count = 0 が返るかを必ず確認しましょう。n が負ならループは 1 回もまわらず 0 を返すのが自然な挙動です。

3 つ目は 戻り値を return し忘れる ケースです。print(count) で出力するだけでは executor は受け取れません。必ず return count で値を返してください。

やってみよう

  • n = 5 を渡すと 5 が返ることを確認する。
  • n = 1000000 を渡したとき、処理がほぼ一瞬で終わることを体感する。これが O(n) の特徴です。
  • 次のレッスンでは入れ子ループを扱います。n = 1000 の 2 重ループは 1000000 回まわるのに対し、1 重ループはたったの 1000 回です。

ループの回数を数える練習は、計算量を見積もる 第一歩 。地味だがここで手を動かしておくと後が楽になる。

Java と Go での実装

Java や Go でも基本のロジックは同じです。for ループのカウンタを 0 から n - 1 まで動かし、本体で count+= 1 するだけです。

Java

public static int countIterations(int n) { int count = 0; for (int i = 0; i < n; i++) { count += 1; } return count; }

Go

func countIterations(n int) int { count := 0 for i := 0; i < n; i++ { count += 1 } return count }

どの言語でも i < n の条件式は変わりません。範囲の表現が range(n)for i = 0; i < n; i++ かで違うだけで、挙動は同じです。

O(1) との対比

O(1) は「n に関係なく一定」の処理です。例えば「配列の先頭要素を返す arr[0]」や「2 つの数の和 a + b」は、データ量が増えても処理時間が変わらないため O(1) です。本問の countIterations(n)n が大きくなるほど時間がかかるので O(n) 。この 入力サイズ依存 の感覚を最初に押さえておくと、後のオーダー比較が楽になります。

O(1) は一定、O(n) は比例、O(log n) は半分ずつ縮める、O(n^2) は 2 乗で増える。この 4 種類だけでもしっかり区別できれば実務で十分通用する。

計算量と実行時間の対応

仮に 1 ステップが 1 ナノ秒 かかるとすると、n = 10^9 (10 億) の O(n) 処理はおよそ 1 秒で終わります。O(n^2) だと 10^18 ステップ必要で、これは現実時間で数十年かかります。O(log n) なら n = 10^9 でも 30 ステップ。オーダーの違いは現実の時間で 億倍 の差 になりうる、というのが計算量を学ぶ最大の動機です。

よくある質問

Q. for と while はどう使い分けますか?

A. 繰り返し回数や対象が決まっているなら for(リスト・range など)が読みやすく、終了条件が動的に決まるなら while を使います。例えば「100 回繰り返す」は for i in range(100):、「ユーザー入力が q になるまで」は while True + break が向いています。

Q. ループの途中で抜けたいときは?

A. break を使うとそのループを即座に終了します。次の周回に進みたいだけなら continue を使い、現在の処理だけスキップします。break / continue は読み手にとってジャンプ先が見えにくいため、関数化して return で抜けると意図が伝わりやすくなります。

Q. インデックスも一緒に取りたい場合は?

A. Python なら for i, v in enumerate(items):、JavaScript なら items.forEach((v, i) => ...) のようにインデックスを同時に取り出せます。手動で i = 0; i += 1 と書くと off-by-one のミスを誘発しやすいので、言語の標準機能を使うのが安全です。

次のレッスン

次は 入れ子ループの実行回数 に進みましょう。

事前確認 — 進む前に次の 3 つができることを確認しましょう。

  1. ループの実行回数 の要点を自分の言葉で説明できる
  2. このレッスンの最小コード (または操作手順) を見ずに書ける
  3. 練習問題やクイズで間違えた箇所を読み直して理解した

理解度チェック (30 秒)

Q. ループの実行回数 とは何か、1 文で説明してください。

この章のポイント

A. 本文の「このレッスンで分かること」または冒頭の説明文を見直し、自分の言葉で要約できれば OK。詰まったら本レッスンの最初の H2 セクションを読み返してみましょう。

関連レッスン

要件

  1. for ループを使って 0 から n-1 まで実行回数を数えること
  2. n <= 0 の場合は 0 を返すこと
  3. 戻り値は整数 (int) であること

入出力例

test-cases.txt

countIterations(5)5 countIterations(0)0 countIterations(1)1 countIterations(10)10 countIterations(100)100 countIterations(-3)0

ヒント

main.py
main.py
学習モード

メモ

forループの実行回数を返す

⌘S で保存