MTでPerlを学ぶ(その13・繰り返しを途中で抜ける)

「MTでPerlを学ぶ」の第13回をお送りします。
今回は、for文やwhile文の繰り返しの中で、途中で繰り返しを抜ける方法を紹介します。

1.繰り返しを途中で抜ける例

for文やwhile文の繰り返しの中で、条件によって繰り返しを抜けたいことは、よくあります。

例えば、「最近30件のブログ記事の中から、画像が貼り付けられている(記事中にimgタグを含む)最新の記事を1件抜き出し、その記事のタイトルを表示する」という処理を考えてみます。
この処理の流れを図で表すと、以下のようになります。


流れ図を大きく表示

この例では、繰り返しの途中で、「記事に画像が含まれているかどうかを条件判断し、含まれていたら、繰り返しから抜ける」という処理があります。

2.last文で繰り返しから抜ける

上の例のように、繰り返しを途中で抜ける場合は、「last」という命令を使います。
forやwhileの繰り返しがあって、その途中で繰り返しを抜けることがある場合、その一般的な処理の流れを図にすると、以下のようになります。


流れ図を大きく表示

この図をプログラムにすると、以下のようになります。

forまたはwhile {
    繰り返し前半の処理
    if (条件) {
        繰り返しから抜ける際の処理
        last;
    }
    繰り返し後半の処理
}

なお、条件を満たした時に、何も処理をせずに即座に繰り返しから抜ける場合、if文の部分を以下のように短縮して書くことができます。

last if (条件);

3.last文を使った例

last文を使った例として、「最近30件のブログ記事の中から、画像が貼り付けられている(記事中にimgタグを含む)最新の記事を1件抜き出し、その記事のタイトルを表示する」をというプログラムを作ると、以下のようになります。

use MT::Entry;

# 最近のブログ記事を30件読み込めるようにする
my $iter = MT::Entry->load_iter({
               blog_id => 1,
               status => MT::Entry::RELEASE(),
           }, {
               limit => 30,
               sort => 'authored_on',
               direction => 'descend'
           });
# 記事を読み込める間繰り返す
while (my $entry = $iter->()) {
    # 記事の本文または追記にimgタグが含まれるかどうかを判断する
    if ($entry->text =~ /<img.*?>/i ||
        $entry->text_more =~ /<img.*?>/i) {
        # 記事のタイトルを出力する
        print $entry->title;
        # 繰り返しを抜ける
        last;
    }
}

上記を含むインデックステンプレートのサンプルをダウンロード

プログラムの内容は以下の通りです。

4~11行目

IDが1番のブログから、最近のブログ記事を30件読み込めるように、「イテレータ」を初期化しています。
イテレータ(iterator)は、ブログ記事等を繰り返して読み込む際に使います。

13行目

記事がある間、イテレータから記事を読み込んで、変数$entryに割り当てます。

15~16行目

記事の本文($entry->text)または追記($entry->text_more)に、imgタグが含まれているかどうかを検索します。

なお、検索には「正規表現」という手法を使っています。
正規表現はいずれ解説する予定です。

18行目

記事にimgタグが含まれている場合、if文の条件が成立して、18行目に処理が進みます。
この行では、記事のタイトル($entry->title)を出力しています。

20行目

imgタグを含む記事が見つかったので、last文で繰り返しから抜けます。