4章は判断木の構成で、データの属するカテゴリと各属性に対する判別結果を入力データとして与え、どの判断を用いて分類すればよいかの選択を支援するプログラムと、後半ではそれを確率探索しています。
後半はまあいいかと思ったので前半部だけ。

/**
  判断木の構成を支援するプログラム
  (判断木を構成するためには、与えられたデータセットを
  適切に分類する属性を選択しなければならない。そこで
  ある属性を選んだ場合にどのように分類されるかを計算
  する。)
  入力は標準入力から与え、出力は標準出力に出力します
  使い方:
    $./decision < (入力ファイル名) > (出力ファイル名)
  入力ファイルでは、属性とカテゴリを0/1で記述します
  出力ファイルには、分類結果を表示します
 **/

#include <iostream>
#include <vector>
#include <sstream>
#include "utf8Func.hpp"
using namespace std;

int stringToInt(const string &str)
{
    int num;
    stringstream ss;
    ss << str;
    ss >> num;
    return num;
}

/**データを読み込んでvectorに格納**/
void readData(vector< vector<int> > &data)
{
    string line;
    while(getline(cin,  line)){
        vector<string> bufferString = split_utf8(line);
        vector<int>    bufferInt;
        for(int i=0; i<bufferString.size(); ++i){
            bufferInt.push_back(stringToInt(bufferString[i]));
        }
        data.push_back(bufferInt);
    }
}

/**属性の評価**/
void evaluateProperty(const vector< vector<int> > &data, const int &i, const int &answer)
{
    int numTotal = 0;
    int numCorrect = 0;
    for(int j=0; j<data.size(); ++j){
        // 求める解答をしているデータがあれば
        if(data[j][i] == answer){
            ++numTotal;
            // 解答が正しい分類に合致していたら
            if(data[j][i] == data[j].back()) ++numCorrect;
        }
    }
    cout << numCorrect << "/" << numTotal << "t"
         << (double)numCorrect/numTotal << endl;
}

int main()
{
    // 解答番号
    const int yes = 1;
    const int no  = 0;

    vector< vector<int> > data;
    readData(data);

    // 各属性による分類
    for(int i=0; i<data[0].size()-1; ++i){
        cout << "property" <<  i+1 << endl;
        // Yesに対応した学習データの数え上げ
        cout << "Yes" << "t";
        evaluateProperty(data,  i,  yes);
        // Noに対応した学習データの数え上げ
        cout << "No" << "t";
        evaluateProperty(data,  i,  no);
        cout << endl;
    }

    return 0;
}

utf8Func.hppはこれ

#ifndef __UTF8FUNC_HPP__
#define __UTF8FUNC_HPP__

#include <vector>
#include <string>

/**utf-8のstringを一文字ずつ分割する**/
std::vector<std::string> split_utf8(const std::string& str) {
    std::vector<std::string> result;
    std::string              tmp;
    bool                     first = true;

    for (size_t i=0; i<=str.size(); ++i) {
        // 各バイトがutf-8の先頭かどうかをチェック
        if (first ||
                (i != str.size() && (str.at(i) & 0xC0) == 0x80)) {
            tmp += str.at(i);
            first = false;
            continue;
        }
        result.push_back(tmp);
        tmp.clear();
        if (i == str.size()) break;
        tmp += str.at(i);
    }
    return result;
};

#endif

5章は遺伝的アルゴリズムはいったん飛ばして、たぶん次は6章のニューラルネットワークのつもり

関連記事

5月分のBanggoodクーポン Mi Pad 4 Plusもあるよ

Kindle Cloud Readerで洋書を読む時にgoogle翻訳を使う

シグマのフルサイズ超広角Artレンズを買った

numpyで3次元座標インデックスの配列を作る方法

300ドル15W中華半導体レーザーカッター買った その5

deep learningフレームワーク・ライブラリをGPU環境のwindows10にインストールする方法と応用まとめ

コメント

コメントを返信する

メールアドレスが公開されることはありません。 * が付いている欄は必須項目です