G-WAN better uses CPU Cores to make the Internet of Things fly thousand times higher ! Leverage legacy servers and low-consumption CPUs to do more with less! With 1GHz in 2000 and 3GHz in 2002 10GHz CPUs were expected in 2005. Today, we should run much faster CPUs but: We're not going to have faster processors. Instead, making software run faster in the future will mean using parallel-programming
例えば移動したディレクトリを記録しているときに、履歴に残っているディレクトリが途中で削除されてしまった場合には、そのディレクトリへ移動できないようにしたり、そのディレクトリを表す項目を淡色表示したい、というようなこともあるでしょう そこで、登録されているコマンドが途中で無効になってしまったような場合には、そのコマンドを無視することができるようにしてみましょう Undo コマンドの基底クラスの実装 #define UNDOREDO_DETACHED 0 #define UNDOREDO_ATTACHED 1 #define UNDOREDO_UNDO 2 #define UNDOREDO_REDO 3 #define UNDOREDO_UNDO_BEGIN 4 #define UNDOREDO_UNDO_END 5 #define UNDOREDO_REDO_BEGIN 6 #define
Undo/Redoの履歴を表示したいときなどがあります このようなときコマンドのグループに名前が付いていると便利です コマンドチェインに名前を付けられるようにしてみましょう Undo コマンド管理クラスの実装 #define INVALID_COMMAND_ID (( uint32_t )-1) #define INVALID_CHAIN_ID (( uint32_t )-1) #define MAXIMUM_CHAIN_LEVEL (( uint32_t )-1) class cundoredoitem { uint32_t m_chain_id; uint32_t m_chain_level; uint32_t m_id; IRestoreObj* m_pRestoreObj; bool dispatch( uint32_t uMsg ); public: void detach();
コマンドのグループ化に対応できるようになりましたが、途中でエラーが発生したときなどに、キャンセルするということができませんでした コマンドチェインを途中でキャンセルできるようにしてみましょう Undo コマンド管理クラスの実装 #define INVALID_COMMAND_ID (( uint32_t )-1) #define INVALID_CHAIN_ID (( uint32_t )-1) #define MAXIMUM_CHAIN_LEVEL (( uint32_t )-1) class cundoredoitem { uint32_t m_chain_id; uint32_t m_chain_level; uint32_t m_id; IRestoreObj* m_pRestoreObj; bool dispatch( uint32_t uMsg ); public: void
一度の操作で複数のコマンドを一括して Undo/Redo したいというときがありますが、前回のコードでは対応していませんでした コマンドのグループ化、コマンドチェインに対応しましょう Undo コマンド管理クラスの実装 #define INVALID_COMMAND_ID (( uint32_t )-1) #define INVALID_CHAIN_ID (( uint32_t )-1) #define MAXIMUM_CHAIN_LEVEL (( uint32_t )-1) class cundoredoitem { uint32_t m_chain_id; uint32_t m_id; IRestoreObj* m_pRestoreObj; bool dispatch( uint32_t uMsg ); public: void detach(); bool attach( uint3
Undo/Redo の際、コマンドチェインの最初と最後のタイミングがわかると便利なときがあります コマンドチェインを実行するときに、最初と最後のタイミングも通知するようにしてみましょう Undo コマンドの基底クラスの実装 最初と最後のタイミングを通知するメッセージを追加します #define UNDOREDO_DETACHED 0 #define UNDOREDO_ATTACHED 1 #define UNDOREDO_UNDO 2 #define UNDOREDO_REDO 3 #define UNDOREDO_UNDO_BEGIN 4 #define UNDOREDO_UNDO_END 5 #define UNDOREDO_REDO_BEGIN 6 #define UNDOREDO_REDO_END 7 class CRestoreObj : public IRestoreObj {
Undo コマンド まずは Undo マネージャに登録するコマンドのインターフェイスを決めましょう Undo マネージャに登録するコマンドはつまり Undo 可能なコマンドということですが、この Undo 可能なコマンドはアプリケーション側が実装するものです そしてこのコマンドは少なくとも Undo マネージャから Undo と Redo の通知を受け取れるようにしておく必要があります このコマンドはどのような形式でもいいのですが、ここでは次のようなインターフェイスを使うことにしましょう #define UNDOREDO_DETACHED 0 #define UNDOREDO_ATTACHED 1 #define UNDOREDO_UNDO 2 #define UNDOREDO_REDO 3 struct IRestoreObj { virtual uint32_t add_ref() =
はじめに どのようなアプリケーションでも Undo 機能はぜひとも欲しい機能の一つだと思いますが、残念ながら Undo を実現するための標準的なフレームワークというようなものは存在しません ですからアプリケーションに Undo の機能を追加しようとすれば一から自分で書く必要があります ここではコマンドリスト形式の Undo の実装について説明しましょう Undo の仕組み Undo の仕組み自体は実はとても簡単です Undo マネージャはコマンドの中身は関知せず、ただコマンドのリストを管理しているだけです コマンドのリストで現在注目しているところを前に戻すのが Undo、先へ進めるのが Redo です 注目している位置より前に変わったコマンドには Redo の通知を送り、先に変わったコマンドには Undo の通知を送ります ただそれだけです コマンドのリストとその注目位置が Undo/Re
はじめに 近年、組み込み環境でもスクリプト言語への関心が高まっていますが、そういった言語処理系を書く際に必要となってくるのが字句解析、構文解析です ここでは簡単な再帰下降型のパーサを例に、実際に実装してみながら構文解析について学んでゆきましょう 再帰下降型の構文解析器は単純に実装するとスタックの消費が激しいことやスタック領域の枯渇の予測が難しいことなどであまり実用的なものにはならないのですが、構造が簡単なので構文解析の仕組みを理解するのには向いています (「再帰降下」でも「再帰下降」でもどっちでもいいです。「recursive descent」の訳かな) BNF 式の構造の定義としてBNF的な表記を用いていますが、別にBNFを知らなくても問題ありません 空文字列(ε)は省略してあります 一部には正規表現的な表記も用いています * は 0回以上の繰り返し、+ は 1回以上の繰り返しを表してい
これまでは負の数を指定する方法がありませんでした 単項演算子をサポートすることで負の数も使えるようにしてみましょう 仕組み 単項演算子も使えるようにしたパーサが処理すべき式は必ず次のような形式になっています 完結式 ::= 部分式_comma 部分式_comma ::= 部分式_add_sub 部分式_comma_ 部分式_comma_ ::= 演算子_comma 部分式_add_sub 部分式_comma_ 演算子_comma ::= , 部分式_add_sub ::= 部分式_mul_div_mod 部分式_add_sub_ 部分式_add_sub_ ::= 演算子_add_sub 部分式_mul_div_mod 部分式_add_sub 演算子_add_sub ::= + あるいは − 部分式_mul_div_mod ::= 部分式_unary 部分式_mul_div_mod_ 部分式
まずは単純に数値の足し算、引き算ができるようにしてみましょう 仕組み パーサが処理すべき式はたぶん次のような形式になっているでしょう 完結式 ::= 部分式 部分式 ::= 数値 演算子 部分式 演算子 ::= + あるいは − 数値 ::= 16進数 あるいは 8進数 あるいは 10進数 16進数 ::= 0x[0-9a-fA-F]+ 8進数 ::= 0[0-7]* 10進数 ::= [1-9][0-9]*「部分式」のところに注目してください 「部分式」の定義に「部分式」自身が含まれていますね つまり定義が再帰的になっているわけです そしてこの定義を上から下へと順番に降りながら解析するので、この手法を「再帰下降型」と呼んでいます このように定義が固まれば後は特に何も考えずにこれをそのまま C++ のコードとして実装すればいいだけです まずパーサに指定されるのは「完結式」の文字列ですから
実はカンマ(,)も演算子です このカンマ演算子を使えるようにしてみましょう 仕組み カンマ演算子も使えるようにしたパーサが処理すべき式は必ず次のような形式になっています 完結式 ::= 部分式_comma 部分式_comma ::= 部分式_add_sub 部分式_comma_ 部分式_comma_ ::= 演算子_comma 部分式_add_sub 部分式_comma_ 演算子_comma ::= , 部分式_add_sub ::= 部分式_mul_div_mod 部分式_add_sub_ 部分式_add_sub_ ::= 演算子_add_sub 部分式_mul_div_mod 部分式_add_sub 演算子_add_sub ::= + あるいは − 部分式_mul_div_mod ::= 定数式 部分式_mul_div_mod_ 部分式_mul_div_mod_ ::= 演算子_mul
演算子の優先順位というものを理解したところで、今度は括弧が使えるようにしてみましょう 仕組み 括弧も使えるようにしたパーサが処理すべき式は必ず次のような形式になっています 完結式 ::= 部分式_add_sub 部分式_add_sub ::= 部分式_mul_div_mod 部分式_add_sub_ 部分式_add_sub_ ::= 演算子_add_sub 部分式_mul_div_mod 部分式_add_sub_ 演算子_add_sub_ ::= + あるいは − 部分式_mul_div_mod ::= 定数式 部分式_mul_div_mod_ 部分式_mul_div_mod_ ::= 演算子_mul_div_mod 定数式 部分式_mul_div_mod_ 演算子_mul_div_mod ::= * あるいは / あるいは % 定数式 ::= 数値 あるいは ( 部分式_add_sub
ここまでの入力文字列中に改行を使うことはできましたが、コメントを書くことはできませんでした そこで入力文字列中に C/C++ 風のコメントがあったときはその部分を無視することができるようにしてみましょう 仕組み コメントは式の評価には関係ないので構文解析器の立場からすると空白と同じです 空白を読み飛ばす関数は skipspace ですから、これをコメント対応に改造してみましょう それだけで全体がコメント対応になります 簡単ですね では実装してみましょう 実装 bool string_calc::skipspace(){ char comment = 0; while( !eof()){ char c1 = at( 0, SEEK_CUR ); char c2 = at( 1, SEEK_CUR ); char c = 0; if( comment == '/' ){ c = getch()
ここまでは解析と評価を一度に行ってきましたが、普通は解析処理と評価/実行の処理を分けるようにします 解析処理は入力文字列が文法に合っているかどうかをチェックしながら出現した演算子や数値などの文法要素を評価の順番に並べたリストを作ることを仕事にします この文法要素を繋げたリストは自然にツリー構造となることから、これを構文木と言います 解析処理は文字列を入力とし、構文木を出力とします 評価/実行処理は構文木を入力とします 評価/実行処理の仕事は構文木を辿って結果を得ることです 構文木はその構造自体によって、演算子の優先順位や演算子の右結合性・左結合性といった問題は自明に解決されているので、単純に先頭から順番に辿って行くだけで結果を得られるような仕組みになっています 仕組み 構文木はツリー構造です ツリー構造の各ノードは枝と葉に分かれます 葉のノードでは「値」が必要です 枝のノードでは「演算子」
これまでのエラーメッセージでは起きたエラーが何かということは判りましたが、それがどこで起きたのかということは判りませんでした そこでエラーメッセージに行番号を加えてどこで発生したエラーなのかも判るようにしてみましょう 仕組み 解析器で改行を数えます 改行文字は必ず空白なので skipspace に手を加えます ノードのメンバには行番号を追加しましょう ノードの実装 class node { size_t m_lineno; . . . public: size_t get_lineno() const { return m_lineno; } . . . void clear(){ m_lineno = ( size_t )-1; m_operator.clear(); m_operands.clear(); m_value.clear(); } void assign( size_t l
これまでは使える数値は整数だけで実数を指定する方法がありませんでした 実数も使えるようにしてみましょう 仕組み 実数も使えるようにしたパーサが処理すべき式は必ず次のような形式になっています 完結式 ::= 部分式_comma 部分式_comma ::= 部分式_add_sub 部分式_comma_ 部分式_comma_ ::= 演算子_comma 部分式_add_sub 部分式_comma_ 演算子_comma ::= , 部分式_add_sub ::= 部分式_mul_div_mod 部分式_add_sub_ 部分式_add_sub_ ::= 演算子_add_sub 部分式_mul_div_mod 部分式_add_sub 演算子_add_sub ::= + あるいは − 部分式_mul_div_mod ::= 部分式_unary 部分式_mul_div_mod_ 部分式_mul_div_
はじめに C++20 の前の基礎知識として、以前 C++ の名前解決 でも紹介した ADL (Argument-dependent name lookup) に関連した話題を少し紹介してみます ■蛇足 ここで「名前を探す」などと言っているのはすべてコンパイル時の話です コンパイラ内部の話です 実行時に関数を探すようなコードが生成されるわけではありません ADL と関数テンプレート 標準に次のような記述があり、通常の関数テンプレート呼び出しには ADL は適用されるが、テンプレート引数を明示的に指定した場合は他の候補の名前が見えていないと ADL は適用されない(呼び出そうとしている Unqualified name がテンプレート関数だと認識されない)。と言っています N1905 14 Templates 14.8 Function template specializations 14.
前回 0 除算の実行時エラーの処理がノードのクラスにありました ノードのクラスなのに実行時のエラー処理まで持っているのは美しくないですね これはノードのクラスに評価器の機能まで持たせてしまっているのが原因でした 構文木と評価器とは分けてしまいましょう そしてついでなので解析器も分けてしまいましょう 仕組み 解析器は、中身自体は今までの string_calc クラスと同じなのですが、エラー処理を分離するためにコールバック用のインターフェイスを持つようにします そしてエラー時にメンバ関数を呼び出していたところをこのインターフェイスのメソッドを呼び出すように置き換えます 評価器は、評価の仕組み自体は同じなので、ノードにあった評価に関連した機能をそのまま評価器に移してしまえばいいだけです ノードの実装 class node { std::string m_operator; std::list<
大規模サイトの性能改善作業とは、どういうものなのか――。リクルートの中古車情報サイト「カーセンサーnet」を全面リニューアルした体験を基に、その実態をレポートする。第1回、第2回はミドルウエアのチューニングを行った。後半はLinuxカーネルに原因があると判明するまでの調査に進む。様々なツールを組み合わせて追跡していった。 中古車情報サイト「カーセンサーnet」の性能試験が本格的に始まって10日目。試験の開始当初は、ブラウザーの表示に10秒もかかるなど目標性能に遠く及ばなかった。しかし前回までで紹介したように、ファイル共有システム「NFS」の設定変更、Webサーバー「Apache」のパラメーター修正、PHPアプリケーションの見直しによって、性能は劇的に向上した。 リクルート入社3年目の私は、今回の性能検証プロジェクトのリーダーとして、得意分野を持つチームメンバーと一緒に対策を進めていた。カッ
The web editor for Mac is back. For people who make delightful, innovative and fast websites — in an app to match. Espresso helps you write, code, design, build and publish with flair and efficiency. Sophisticated text features, amazing Live Preview with Browser Xray, CSSEdit tools, the Navigator, Dynamo auto-building, and Server Sync. Whether you're starting from scratch or tweaking a live site,
リリース、障害情報などのサービスのお知らせ
最新の人気エントリーの配信
j次のブックマーク
k前のブックマーク
lあとで読む
eコメント一覧を開く
oページを開く