破壊的クラス拡張のスコープを制限 する モジュール機構...
DESCRIPTION
破壊的クラス拡張のスコープを制限 する モジュール機構 の意味論およびその実装方法. ++. +, ++. 竹下 若菜,赤井 駿平,千葉 滋 + 東京大学 創造情報学専攻 ++ 東京工業大学 数理・計算学専攻. +. 破壊的クラス拡張. 既存のコードを変更せずに 既存のクラスにメソッドの追加・再定義 コードの再利用 サブクラスに関する変更・オブジェクト 生成部分の 書き換えが不必要. class Window{ : void setBorder (){ // WindowsXP の // フレームのボーダー } - PowerPoint PPT PresentationTRANSCRIPT
+
破壊的クラス拡張のスコープを制限するモジュール機構の意味論およびその実装方法竹下 若菜,赤井 駿平,千葉 滋
+ 東京大学 創造情報学専攻++ 東京工業大学 数理・計算学専攻
+ ++ +, ++
+破壊的クラス拡張既存のコードを変更せずに
既存のクラスにメソッドの追加・再定義コードの再利用
サブクラスに関する変更・オブジェクト生成部分の書き換えが不必要
Window クラス
Frame クラス Dialog クラス
class Window{ : void setBorder(){ //WindowsXP の // フレームのボーダー }}
win7 パッケージrevise Window{
}
void setBorder(){ //Windows7 の // フレームのボーダー}
void setBorder(){ //Windows7 の // フレームのボーダー}
2
+例:ウィジェットを破壊的クラス拡張する2 種類の look&feel を持ったアプリケーションを作る
Windows 7 の look&feel だが、ボーダーだけはこのアプリケーション専用のデザイン 管理者権限認証時だけは特別な look&feel
インストール時など ウイルスに偽パネルを出されにくいように
3
+同じクラスに対して破壊的クラス拡張を複数行うとメソッド名が衝突する危険性
多重再定義の危険revise Window{
}revise Window{
}
class Window{ void setButtonColor(){ //WindowsXP デザイン } void setSize(){ ・・・・ } void setBorder(){ //WindowsXP の // フレームのボーダー }}
元クラス
authentication パッケージ
win7 パッケージ
void setBorder(){ // 管理者権限認証用の // フレームのボーダー}
void setBorder(){ //Windows7 の // フレームのボーダー}void setButtonColor(){ //Windows7 デザイン}
app パッケージrevise Window{
}
void setBorder(){ // アプリケーションの // フレームのボーダー}
void setBorder(){ // 管理者権限認証用の // フレームのボーダー}
void setBorder(){ //Windows7 の // フレームのボーダー}void setButtonColor(){ //Windows7 デザイン}
void setBorder(){ // アプリケーションの // フレームのボーダー}
多重再定義
4
+用途に応じた柔軟なスコーピング用途に応じた柔軟なスコーピングが必要
スコーピングはメソッド名衝突を回避する方法の一つ 破壊的クラス拡張の影響範囲を制限
既存のスコーピングは固定的 Ruby: 最新の定義が有効 ( スコープは制限しない ) Ruby の Refinements: 有効な静的スコープを指定 Classboxes: 有効な動的スコープを指定
5
+提案 : モジュール機構 Method Shelters様々なスコーピングをとることができるモジュール機構
モジュール:シェルター 破壊的クラス拡張と require 宣言を持つ require 宣言で他のシェルターをシェルター内に取り込むことができる
取り込んだシェルター内の破壊的クラス拡張はそのシェルターで定義したかのように扱える2種類の require
使い分けることで様々なスコーピングを可能に 動的なスコーピングの中に静的なスコーピングを実現
exposedly require と hiddenly require
6
+
requires win7;requires hiddenly authentication;revise Window{ void setBorder(){ // アプリケーション用のボーダー } void install(){ : checkPass(); : makeFrame(); : }}}
revise Window{ 権限認証用の // フレームのボーダー } void setButtonColor(){…} void checkPass(){
: setBorder(); :
win7 シェルター authentication シェルター
app シェルター
revise Window{
: setBorder(); :
void setBorder(){ //windows7 用の // フレームのボーダー }void setButtonColor(){…}void makeFrame(){ : setBorder(); : }
void setBorder(){ // 管理者権限認証用の // フレームのボーダー } void setButtonColor(){…} void checkPass(){
: setBorder(); : }}
void setBorder(){ // アプリケーション用のボーダー }void install(){ : checkPass(); : makeFrame(); : }}}
7exposedl
y hiddenly
+
requires app;update_app シェルター
exposedly require
推移的な require require したシェルター中のメソッド定義をさらに再定義できる 繰り返しシェルターを
require することでメソッドを何度も再定義可能
app シェルター requires win7; requires hiddenly auth; : makeFrame();
win7 シェルター authentication シェルターvoid makeFrame(){ :}
void makeFrame(){ :}
呼び出し 呼び出し
8
+hiddenly require
非推移的な require require したメソッド定義をさらに再定義することはできない 他のシェルターに影響を与えない・影響されない
requires app;update_app シェルター
app シェルター
void checkPass(){ :}
requires win7; requires hiddenly auth; : checkPass();
authentication シェルターvoid checkPass(){ :}
win7 シェルター
呼び出し
9
+シェルターによるスコーピング2 種類の require で柔軟なスコーピング既存のスコーピングも可能
Ruby の Refinements hiddenly require で実現可能
Classboxes exposedly require で実現可能
10
+メソッド探索 11
ここから探索
ここから探索メソッド呼び出し
メソッド呼び出しルートから探索
再定義されている可能性があるため
A
B
C
D
E
F
G
+メソッド探索の実装方法実行時の文脈に依存したメソッド探索
コールスタックによりパスをチェックし、呼び出すメソッド定義を決定
authenticationwin7
stdGUI
app
void update(){ setBorder(); }
setBorder の定義
12
appWindow.install
authenticationWindow.checkPass
stdGUIWindow.update
コールスタック
authenticationWindow.setBorder
< シェルター名 >< クラス名 >.< メソッド名 >
+効率の良い実装方法コンパイル時に変更
1. コールスタックを探索せずにメソッド定義を決定できるようにする2. クラス名とメソッド名のみで探索ができるようにする
通常のメソッド探索のコストに近づける 操作的な定義を素朴に実装すると実行時間のコストがかかる
13
+実行時にコールスタックを見る必要をなくす
シェルターの require 関係の木構造を静的解析 コールスタックを探索せずにメソッドを決定 ノード毎に一意なメソッド定義が決定
ACB
D
A
AB AC
ABD ACD
14効率の良い実装方法 1
DDDD
+効率の良い実装方法2クラス名とメソッド名のみでメソッド探索を可能に
一意に決定したメソッド定義のメソッド名を変更 メソッド名とメソッド定義が一対一に対応
メソッド呼び出し元も書き換える
ABD ノード
void setFrame{ setBorder();}
void setBorder(){ //win7 のボーダー}
呼び出し
void setFrame{ setBorder_ABD();}
void setBorder_ABD(){ //win7 のボーダー}
呼び出し
ABD ノード
15
変更前
変更後
+形式化 16
操作的な定義の形式化 実装方法の形式化
+関連研究前身研究: Method Shelters[ 赤井・千葉 AOSD ’12]
chamber によってシェルターの中を二つに分ける hidden chamber と exposed chamber chamber の中に破壊的クラス拡張とインポート宣言 インポートは一種類
形式化がない
破壊的クラス拡張は以下の言語に実装されている Smalltalk, Ruby, AspectJ, MultiJava,GluonJ……..
Classbox/J Classboxes を Java に導入した
17
+まとめモジュール機構 Method Shelters
2 種類の require で様々なスコーピングを可能に exposedly な require と hiddenly な require
実装前と同コストでメソッド探索が可能な実装方法の提案 形式化
今後の予定 実際に Java に実装してみる
18