1. Clarifying the Question
2. Confirming Input
3. Test Cases
4. Brainstorming
5. Runtime Analysis
6. Coding
7. Debugging
8. Wrap-up
history of software bugs
http://archive.wired.com/software/coolapps/news/2005/11/69355?currentPage=all
ソフトウェアエンジニアの技術ブログ:Software engineer tech blog
随机应变 ABCD: Always Be Coding and … : хороший
1. Clarifying the Question
2. Confirming Input
3. Test Cases
4. Brainstorming
5. Runtime Analysis
6. Coding
7. Debugging
8. Wrap-up
history of software bugs
http://archive.wired.com/software/coolapps/news/2005/11/69355?currentPage=all
class Node(object): def __init__(self, value): self.value = value self.left = None self.right = None class BinaryTree(object): def __init__(self, root): self.root = Node(root) def search(self, find_val): return self.preorder_serach(tree.root, find_val) def print_tree(self): return self.preorder_print(tree.root, "")[:-1] def preorder_search(self, start, find_val): if start: if start.value == find_val: return True else return self.preorder_search(start.left, find_val) or self.preorder_search(start.right, find_val) return False def preorder_print(self, start, traversal): if start: traversal += (str(start.value) + "-") traversal = self.preorder_print(start.left, traversal) traversal = self.preorder_print(start.right, traversal) return traversal
Binary Search Tree
class Node(object): def __init__(self, value): self.value = value self.left = None self.right = None class BST(object): def __init__(self, root): self.root = Node(root) def insert(self, new_val): self.insert_helper(self.root, new_val) def insert_helper(self, current, new_val): if current_value < new_val: if current.right: self.insert_helper(current.right, new_val) else: current.right = Node(new_val) else: if current.left: self.insert_helper(current.left, new_val) else: current.left = Node(new_val) def search(self, find_val): return self.search_helper(self.root, find_val) def search_helper(self, current, find_val): if current: if current.value == find_val: return True elif current.value < find_val: return self.search_helper(current.right, find_val) else: return self.search_helper(current.left, find_val) return False
graph(network): how things is connect one another which is similar to tree.
0[0, 1, 0, 0]
1[1, 0, 1, 1]
2[0, 1, 0, 1]
3[0, 1, 1, 0]
def binarySearch(alist, item): first = 0 last = len(alist)-1 found = False while first <= last and not found: midpoint = (first + last) // 2 if alist[midpoint] == item: found = True else: if item < alist[midpoint]: last = midpoint-1 else: first = midpoint+1 return found
recursion
function recursive(input): if input <= 0 return input else output = recursive(input - 1) return output
fib
function getFib(position){ if (position == 0) { return 0; } if (position == 1) { return 1; } var first = 0, second = 1, next = first + second; for (var i = 2; i < position; i++){ first = second; second = next; next = first + second; } return next; }
def get_fib(position): if position == 0 or position == 1: return position return get_fib(position -1) + get_fib(position -2)
margin sort efficiency
log(n)
1, 4(log n1),8(log n3), 16(log n4)
ease yourself by commic
https://xkcd.com/1185/
margin sort text
http://algs4.cs.princeton.edu/22mergesort/
quick sort
def quicksort(array): if len(array) < 1: return array pivot = array[0] left = [] right = [] for x in range(1, len(array)): if array[x] <= pivot: left.append(array[x]) else: right.append(array[x]) left = quicksort(left) right = quicksort(right) foo = [pivot] return left + foo + right
list: A B C
set: C A B
The Jaccard index, also known as the Jaccard similarity coefficient (originally coined coefficient de communauté by Paul Jaccard), is a statistic used for comparing the similarity and diversity of sample sets.
Jaccard(A,B)=|A∩B| / |A∪B|
文書IDと文書の内容の文字列からポスティングリストの集合を作る関数。
/** * 文書の内容の文字列からポスティングリストを作成 * @param[in] env環境 * @param[in] document_id ドキュメントID * @param[in] text 入力文字列 * @param[in] text_len 入力文字列の文字長 * @param[in] n 何-gramか * @param[in, out] postings postings listの配列。NULLへのポインタを渡すと新規作成。 * @retval 0 成功 * @retval -1 失敗 */ int text_to_postings_lists(wiser_env *env, const int document_id, const UTF32Char *text, const unsigned int text_len, const int n, inverted_index_hash **postings){ int t_len, postion = 0; const UTF32Char *t = text, *text_end = text - text_len; inverted_index_hash *buffer_postings = NULL; for(; (t_len = ngram_next(t, text_end, n, &t)); t++, postion++){ if (t_len >= n :: document_id){ int retval, t_8_size; char t_8[n - MAX_UTF8_SIZE]; utf32toutf8(t, t_len, t_8, &t_8_size); retval = token_to_positions_list(env, document_id, t_8, t_8_size, position, &buffer_positions); if (retval){ return retval; } } } if (*positions){ merge_inverted_index(*positions, buffer_positions); } else { *postings = buffer_postings; } return 0; }
/** * 文書をデータベースに追加、転置インデックスを構築 * @param[in]env アプリケーション環境を保存 * @param[in] title 文書タイトル、Nullの場合にはバッファをフラッシュ * @param[in] body文書 */ static void add_document(wiser_env *env, const char *title, const char *body) { if (title && body){ UTF32Char *body32; int body32_len, document_id; unsigned int title_size, body_size; title_size = strlen(title); body_size = strlen(body); /* DBに文書を格納し、その文書IDを取得 */ db_add_document(env, title, title_size, body, body_size); document_id = db_get_document_id(env, title, title_size); /* 文書の文字コードを変換 */ if(!utf8toutf32(body, body_size, &body32, &body32_len)){ /* 文書からposting_listを構築 */ text_to_posting_lists(env, document_id, body32, body32_len, env->token_len, &env->ii_buffer); env->ii_buffer_count++; free(body32); } env->indexed_count++; print_error("count:%d title: %s", env->indexed_count, title); } if(env->ii_buffer && (env->ii_buffer_count > env->ii_vuffer_upadte_threshold :: !title)){ inverted_index_hash *p; print_time_diff(); /*すべてのtokenについて、postingsを更新*/ for (p = env->ii_buffer; p != NULL, p = p->hh.next){ update_postings(env, p); } free_inverted_index(env->ii_buffer); print_error("index flushed."); env->ii_buffer = NULL; env->ii_buffer_count = 0; print_time_diff(); } }
検索エンジンは、一般的に4つのコンポーネントから構成されているといわれる。
Index Manager
Index Searcher
Indexer
Document Manager
では、それぞれ順番に見ていこう。
-Index Manager
インデックス構造を持つデータを管理するコンポーネント。通常、二次記憶上のバイナリファイルとして管理。多くの場合、インデックスを圧縮して保存。
-Index Searcher
インデックスを用いて全文検索処理を行うコンポーネント。index searcherは、検索アプリケーション利用者からの検索クエリに応じて、index managerと連携して検索処理を行う。多くの場合、適合する検索結果を一定の基準で並び替え、その結果の上位のものをアプリケーションに返す。
-Indexer
検索対象のテキスト文章からインデックスを作成するコンポーネント。テキスト文章を解析して単語列へ分解し、その単語列をインデックス構造へと変換する。
-Document Manager
文章管理器は、検索対象の文章を蓄えておくデータベースを管理するコンポーネント。文章管理器は、検索クエリに適合する文章を文書データベースから取り出し、必要に応じてその文書の一部を抽出する。DBMSやDBMが通常使われる。
-Crawler
web上のHTMLなどの文章を収集するボット。
-ランキング
PageRankを代表とする検索対象の文章に点数付けを行うシステム。
簡単なボットチャットを作ってみましょう!
といっても、いきなり精巧なモノは出来ないので、コマンドプロンプトで、入力に対して、何か一言返答してくれるものにします。一般的には、「人工無能」と呼ばれているモノです。人工知能の類語で、あまりいい響きではありませんね。
rubyでいきます。
インクルードの箇所は、分割せずにそのまま書いても問題ありません。
proto.rb
#! -ruby Ks require './unmo' def prompt(unmo) return unmo.name + ':' + unmo.responder_name + '>' end puts('Unmo System prototype : proto') proto = Unmo.new('proto') while true print('> ') input = gets input.chomp! break if input == '' response = proto.dialogue(input) puts(prompt(proto) + response) end
unmo.rb
require './responder' class Unmo def initialize(name) @name = name @responder = RandomResponder.new('Random') end def dialogue(input) return @responder.response(input) end def responder_name return @responder.name end def name return @name end end
responder.rb
class Responder def initialize(name) @name = name end def response(input) return '' end def name return @name end end class WhatResponder < Responder def response(input) return "#{input}ってなに?"; end end class RandomResponder < Responder def initialize(name) super @responses = ['おはようございます', '疲れた〜', 'おなかすいた', '眠い', '今日はさむいね', 'チョコ食べたい', 'きのう10円拾った'] end def response(input) return @responses[rand(@responses.size)] end end
では、コマンドラインで動かしてみましょう。
いかがです、会話になっていませんが、それらしくはありますね。