1. はじめに
プログラミング言語 C++では「ラムダ式」と呼ばれるものが使えるようになり(C++11で採用され、C++14で改良された)、標準ライブラリのアルゴリズムの利用がより簡潔な記述でできるようになりました。
この記事では、基本に立ち返って、どのようにしてアルゴリズムを記述し、それを利用するかを考えたいと思います。
汎用的なアルゴリズムをどのように記述すると良いのか、そしてそのアルゴリズムがどのように使われると良いのか、を述べます。その中で、何故ラムダ式が便利なのか、その理由が分かってもらえれば幸いです。
次の記事の姉妹記事です。そちらではこの記事をC#用にしています。併せて読まれるとC++との違いが分かると思います。
対象読者
- C++で開発を行っている方
- 初級から中級にステップアップしたいC++プログラマーの方
必要な環境
Visual Studio 2013(注1)など、C++11以上のC++(ラムダ式が使えるC++)がコンパイル・実行できる環境。
2. 最初のプログラム
まず、C++で書いたサンプルプログラムを一つ用意します。
このサンプルプログラムは、出版社クラス Publisherと書籍クラス Bookを持ちます。メインの部分では、PublisherとBookのコレクションをそれぞれ持ち、その中からある条件に一致したものを表示します。
出版社クラス Publisher
#pragma once
#include <string>
class Publisher
{
std::wstring name;
public:
Publisher(std::wstring name) : name(name)
{}
std::wstring GetName() const
{ return name; }
};
書籍クラス Book
出版社のインデックスを持っています。
#pragma once
#include <string>
class Book
{
std::wstring code;
std::wstring title;
unsigned int publisherIndex;
public:
Book(std::wstring code, std::wstring title, int publisherIndex)
: code(code), title(title), publisherIndex(publisherIndex)
{}
std::wstring GetCode() const
{ return code; }
std::wstring GetTitle() const
{ return title; }
int GetPublisherIndex() const
{ return publisherIndex; }
};
この2つのクラスのインスタンスのそれぞれのコレクションを作り、その中から「特定の文字列を名称に含むもの」を表示してみます。 例えば、書籍のタイトルまたは出版社の名前に "リ" を含むものをコンソールに表示してみましょう。
メイン プログラム(書籍のタイトルまたは出版社の名前に "リ" を含むものをコンソールに表示)
#include <iostream>
#include <list>
#include <vector>
#include <string>
using namespace std;
#include "Book.h"
#include "Publisher.h"
class Program
{
public:
void Run()
{
const vector<Publisher> publisherList = {
Publisher(L"技術評論社" ),
Publisher(L"翔泳社" ),
Publisher(L"オライリー・ジャパン"),
Publisher(L"SBクリエイティブ" )
};
const list<Book> bookList = {
Book(L"4774157155", L"C++ ポケットリファレンス" , 0),
Book(L"4798108936", L"C++ の絵本" , 1),
Book(L"4798119768", L"独習 C++ 第4版" , 1),
Book(L"4873110637", L"C++ プログラミング入門" , 2),
Book(L"4797376686", L"C++ テンプレートテクニック 第2版", 3)
};
const wstring searchWord = L"リ";
for (list<Book>::const_iterator iterator = bookList.begin();
iterator != bookList.end(); iterator++) {
const wstring publisherName =
publisherList[iterator->GetPublisherIndex()].GetName();
if (iterator->GetTitle().find(searchWord) != wstring::npos ||
publisherName.find(searchWord) != wstring::npos)
wcout << L"コード: " << iterator->GetCode()
<< L", タイトル: " << iterator->GetTitle()
<< L", 出版社: " << publisherName
<< endl;
}
}
};
int main()
{
wcout.imbue(locale("Japanese", locale::ctype));
Program().Run();
return 0;
}
実行してみると、次のようにタイトルまたは出版社の名前に "リ" を含む書籍が表示されます。
コード: 4774157155, タイトル: C++ ポケットリファレンス, 出版社: 技術評論社 コード: 4873110637, タイトル: C++ プログラミング入門, 出版社: オライリー・ジャパン コード: 4797376686, タイトル: C++ テンプレートテクニック 第2版, 出版社: SBクリエイティブ
