<?xml version="1.0" encoding="UTF-8" ?> <rss version="2.0" xmlns:dc="http://purl.org/dc/elements/1.1/" xmlns:trackback="http://madskills.com/public/xml/rss/module/trackback/" xmlns:wfw="http://wellformedweb.org/CommentAPI/" xmlns:slash="http://purl.org/rss/1.0/modules/slash/"><channel><title>設計思想</title><link>http://blogs.wankuma.com/kzt/category/2098.aspx</link><description>設計思想に関するエントリ</description><managingEditor>kazuto</managingEditor><dc:language>ja-JP</dc:language><generator>.Text Version 0.95.2004.102</generator><item><dc:creator>kazuto</dc:creator><title>[設計思想] DIの使用場面・使用方法</title><link>http://blogs.wankuma.com/kzt/archive/2009/02/02/167292.aspx</link><pubDate>Mon, 02 Feb 2009 14:16:00 GMT</pubDate><guid>http://blogs.wankuma.com/kzt/archive/2009/02/02/167292.aspx</guid><wfw:comment>http://blogs.wankuma.com/kzt/comments/167292.aspx</wfw:comment><comments>http://blogs.wankuma.com/kzt/archive/2009/02/02/167292.aspx#Feedback</comments><slash:comments>10</slash:comments><wfw:commentRss>http://blogs.wankuma.com/kzt/comments/commentRss/167292.aspx</wfw:commentRss><trackback:ping>http://blogs.wankuma.com/kzt/services/trackbacks/167292.aspx</trackback:ping><description>最近DI（Dependency Injection）やAOP（Acpect Oriented Programming）について凄く興味が出て勉強してます。&lt;br&gt;
そこでDIコンテナや、AOPを実現する為の機能を趣味で作成しているのですが、いまいち理解出来ない事があります。&lt;br&gt;
&lt;br&gt;
自分の認識としては、DIはクラス間の依存部分を外部へ排除し、依存部分を外部より注入する機構を適用し、管理・修正に強くするといった認識です。（すでにここから違うのか？）&lt;br&gt;
まず再確認として下記のようなクラスがあるとします。&lt;br&gt;
&lt;br&gt;
&lt;div class="codename"&gt;Employee&lt;/div&gt;
&lt;div class="code"&gt;
&lt;div style="font-family: メイリオ; font-size: 8pt; color: black; background: white;"&gt;
&lt;span style="color: blue;"&gt;Public&lt;/span&gt; &lt;span style="color: blue;"&gt;Class&lt;/span&gt; Employee
&lt;br&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; &lt;span style="color: blue;"&gt;Private&lt;/span&gt; shoutLogic &lt;span style="color: blue;"&gt;As&lt;/span&gt; HardShoutLogic
&lt;br&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; &lt;span style="color: blue;"&gt;Public&lt;/span&gt; &lt;span style="color: blue;"&gt;Sub&lt;/span&gt; Shout()
&lt;br&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; &amp;nbsp;&amp;nbsp;&amp;nbsp; shoutLogic = &lt;span style="color: blue;"&gt;New&lt;/span&gt; HardShoutLogic()
&lt;br&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; &amp;nbsp;&amp;nbsp;&amp;nbsp; Console.WriteLine(shoutLogic.GetShoutString() &amp;amp; &lt;span style="color: #a31515;"&gt;"&amp;#21483;&amp;#12406;&amp;#65374;&amp;#65374;&amp;#65281;&amp;#65281;&amp;#65281;"&lt;/span&gt;)
&lt;br&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; &lt;span style="color: blue;"&gt;End&lt;/span&gt; &lt;span style="color: blue;"&gt;Sub&lt;/span&gt;
&lt;br&gt;&lt;span style="color: blue;"&gt;End&lt;/span&gt; &lt;span style="color: blue;"&gt;Class&lt;/span&gt;
&lt;/div&gt;
&lt;/div&gt;
&lt;br&gt;
&lt;div class="codename"&gt;HardShoutLogic&lt;/div&gt;
&lt;div class="code"&gt;
&lt;div style="font-family: メイリオ; font-size: 8pt; color: black; background: white;"&gt;
&lt;span style="color: blue;"&gt;Public&lt;/span&gt; &lt;span style="color: blue;"&gt;Class&lt;/span&gt; HardShoutLogic
&lt;br&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; &lt;span style="color: blue;"&gt;Public&lt;/span&gt; &lt;span style="color: blue;"&gt;Function&lt;/span&gt; GetShoutString() &lt;span style="color: blue;"&gt;As&lt;/span&gt; &lt;span style="color: blue;"&gt;String&lt;/span&gt;
&lt;br&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; &amp;nbsp;&amp;nbsp;&amp;nbsp; &lt;span style="color: blue;"&gt;Return&lt;/span&gt; &lt;span style="color: #a31515;"&gt;"&amp;#28608;&amp;#12375;&amp;#12367;"&lt;/span&gt;
&lt;br&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; &lt;span style="color: blue;"&gt;End&lt;/span&gt; &lt;span style="color: blue;"&gt;Function&lt;/span&gt;
&lt;br&gt;&lt;span style="color: blue;"&gt;End&lt;/span&gt; &lt;span style="color: blue;"&gt;Class&lt;/span&gt;
&lt;/div&gt;
&lt;/div&gt;
&lt;br&gt;
従業員が叫ぶと言う事は別として、上記ではEmployeeを叫ばす為に、どのように叫ばすかを実装しているHardShoutLogicクラスが必要になってます。&lt;br&gt;
Employeeクラス内でHardShoutLogicクラスのインスタンスが生成されていますので、EmployeeクラスはHardShoutLogicクラスに依存している事になります。&lt;br&gt;
例えば、「激しく叫ぶ～～！」を「弱く叫ぶ・・・」にする為にはWeakShoutLogicクラスが必要になります。&lt;br&gt;
&lt;br&gt;
&lt;div class="codename"&gt;WeakShoutLogic&lt;/div&gt;
&lt;div class="code"&gt;
&lt;div style="font-family: メイリオ; font-size: 8pt; color: black; background: white;"&gt;
&lt;span style="color: blue;"&gt;Public&lt;/span&gt; &lt;span style="color: blue;"&gt;Class&lt;/span&gt; WeakShoutLogic
&lt;br&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; &lt;span style="color: blue;"&gt;Public&lt;/span&gt; &lt;span style="color: blue;"&gt;Function&lt;/span&gt; GetShoutString() &lt;span style="color: blue;"&gt;As&lt;/span&gt; &lt;span style="color: blue;"&gt;String&lt;/span&gt;
&lt;br&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; &amp;nbsp;&amp;nbsp;&amp;nbsp; &lt;span style="color: blue;"&gt;Return&lt;/span&gt; &lt;span style="color: #a31515;"&gt;"&amp;#24369;&amp;#12367;"&lt;/span&gt;
&lt;br&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; &lt;span style="color: blue;"&gt;End&lt;/span&gt; &lt;span style="color: blue;"&gt;Function&lt;/span&gt;
&lt;br&gt;&lt;span style="color: blue;"&gt;End&lt;/span&gt; &lt;span style="color: blue;"&gt;Class&lt;/span&gt;
&lt;/div&gt;
&lt;/div&gt;
&lt;br&gt;
WeakShoutLogicクラスを使用すればEmployeeクラスは激しくも弱くも叫ぶ事が出来るようになりますが、依然Employeeクラスでは実装クラスを直接使用している為に、依存性が存在する事は無くなっていません。&lt;br&gt;
ここで、インターフェイスとファクトリクラスを使用して、Employeeクラスから叫ぶ実装のインスタンス生成を排除して依存性を弱くします。&lt;br&gt;
&lt;br&gt;
&lt;div class="codename"&gt;IShoutLogic&lt;/div&gt;
&lt;div class="code"&gt;
&lt;div style="font-family: メイリオ; font-size: 8pt; color: black; background: white;"&gt;
&lt;span style="color: blue;"&gt;Public&lt;/span&gt; &lt;span style="color: blue;"&gt;Interface&lt;/span&gt; IShoutLogic
&lt;br&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; &lt;span style="color: blue;"&gt;Function&lt;/span&gt; GetShoutString() &lt;span style="color: blue;"&gt;As&lt;/span&gt; &lt;span style="color: blue;"&gt;String&lt;/span&gt;
&lt;br&gt;&lt;span style="color: blue;"&gt;End&lt;/span&gt; &lt;span style="color: blue;"&gt;Interface&lt;/span&gt;
&lt;/div&gt;
&lt;/div&gt;
&lt;br&gt;
&lt;div class="codename"&gt;HardShoutLogic&lt;br&gt;（IShoutLogic実装版）&lt;/div&gt;
&lt;div class="code"&gt;
&lt;div style="font-family: メイリオ; font-size: 8pt; color: black; background: white;"&gt;
&lt;span style="color: blue;"&gt;Public&lt;/span&gt; &lt;span style="color: blue;"&gt;Class&lt;/span&gt; HardShoutLogic
&lt;br&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; &lt;span style="color: blue;"&gt;Implements&lt;/span&gt; IShoutLogic
&lt;br&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; &lt;span style="color: blue;"&gt;Public&lt;/span&gt; &lt;span style="color: blue;"&gt;Function&lt;/span&gt; GetShoutString() &lt;span style="color: blue;"&gt;As&lt;/span&gt; &lt;span style="color: blue;"&gt;String&lt;/span&gt; &lt;span style="color: blue;"&gt;Implements&lt;/span&gt; IShoutLogic.GetShoutString
&lt;br&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; &amp;nbsp;&amp;nbsp;&amp;nbsp; &lt;span style="color: blue;"&gt;Return&lt;/span&gt; &lt;span style="color: #a31515;"&gt;"&amp;#28608;&amp;#12375;&amp;#12367;"&lt;/span&gt;
&lt;br&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; &lt;span style="color: blue;"&gt;End&lt;/span&gt; &lt;span style="color: blue;"&gt;Function&lt;/span&gt;
&lt;br&gt;&lt;span style="color: blue;"&gt;End&lt;/span&gt; &lt;span style="color: blue;"&gt;Class&lt;/span&gt;
&lt;/div&gt;
&lt;/div&gt;
&lt;br&gt;
&lt;div class="codename"&gt;WeakShoutLogic&lt;br&gt;（IShoutLogic実装版）&lt;/div&gt;
&lt;div class="code"&gt;
&lt;div style="font-family: メイリオ; font-size: 8pt; color: black; background: white;"&gt;
&lt;span style="color: blue;"&gt;Public&lt;/span&gt; &lt;span style="color: blue;"&gt;Class&lt;/span&gt; WeakShoutLogic
&lt;br&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; &lt;span style="color: blue;"&gt;Implements&lt;/span&gt; IShoutLogic
&lt;br&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; &lt;span style="color: blue;"&gt;Public&lt;/span&gt; &lt;span style="color: blue;"&gt;Function&lt;/span&gt; GetShoutString() &lt;span style="color: blue;"&gt;As&lt;/span&gt; &lt;span style="color: blue;"&gt;String&lt;/span&gt; &lt;span style="color: blue;"&gt;Implements&lt;/span&gt; IShoutLogic.GetShoutString
&lt;br&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; &amp;nbsp;&amp;nbsp;&amp;nbsp; &lt;span style="color: blue;"&gt;Return&lt;/span&gt; &lt;span style="color: #a31515;"&gt;"&amp;#24369;&amp;#12367;"&lt;/span&gt;
&lt;br&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; &lt;span style="color: blue;"&gt;End&lt;/span&gt; &lt;span style="color: blue;"&gt;Function&lt;/span&gt;
&lt;br&gt;&lt;span style="color: blue;"&gt;End&lt;/span&gt; &lt;span style="color: blue;"&gt;Class&lt;/span&gt;
&lt;/div&gt;
&lt;/div&gt;
&lt;br&gt;
&lt;div class="codename"&gt;Employee&lt;br&gt;（ファクトリ使用版）&lt;/div&gt;
&lt;div class="code"&gt;
&lt;div style="font-family: メイリオ; font-size: 8pt; color: black; background: white;"&gt;
&lt;span style="color: blue;"&gt;Public&lt;/span&gt; &lt;span style="color: blue;"&gt;Class&lt;/span&gt; Employee
&lt;br&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; &lt;span style="color: blue;"&gt;Private&lt;/span&gt; shoutLogic &lt;span style="color: blue;"&gt;As&lt;/span&gt; IShoutLogic
&lt;br&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; &lt;span style="color: blue;"&gt;Public&lt;/span&gt; &lt;span style="color: blue;"&gt;Sub&lt;/span&gt; Shout()
&lt;br&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; &amp;nbsp;&amp;nbsp;&amp;nbsp; &lt;span style="color: green;"&gt;'&amp;#12501;&amp;#12449;&amp;#12463;&amp;#12488;&amp;#12522;&amp;#12463;&amp;#12521;&amp;#12473;&amp;#12434;&amp;#20351;&amp;#29992;&amp;#12375;IShoutLogic&amp;#23455;&amp;#35013;&amp;#12463;&amp;#12521;&amp;#12473;&amp;#12434;&amp;#21462;&amp;#24471;&amp;#12377;&amp;#12427;&lt;/span&gt;
&lt;br&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; &amp;nbsp;&amp;nbsp;&amp;nbsp; shoutLogic = ShoutLogcFactory.GetShoutLogic()
&lt;br&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; &amp;nbsp;&amp;nbsp;&amp;nbsp; Console.WriteLine(shoutLogic.GetShoutString() &amp;amp; &lt;span style="color: #a31515;"&gt;"&amp;#21483;&amp;#12406;&amp;#65374;&amp;#65374;&amp;#65281;&amp;#65281;&amp;#65281;"&lt;/span&gt;)
&lt;br&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; &lt;span style="color: blue;"&gt;End&lt;/span&gt; &lt;span style="color: blue;"&gt;Sub&lt;/span&gt;
&lt;br&gt;&lt;span style="color: blue;"&gt;End&lt;/span&gt; &lt;span style="color: blue;"&gt;Class&lt;/span&gt;
&lt;/div&gt;
&lt;/div&gt;
&lt;br&gt;
上記変更にてEmployeeクラスよりIShoutLogic実装クラスのインスタンス生成をファクトリクラスへカプセル化する事が出来ました。&lt;br&gt;
これでIShoutLogic派生クラスの変更があってもファクトリクラスを修正するだけで良くなりました。&lt;br&gt;
&lt;br&gt;
Seasar.NETをベースに話しをしますが、この状態からDIを使用し依存性を外部に出す場合、Seasar.NETのS2Container.NETを使用し外部ファイルベースのDIを適用するか、Quillを使用し属性ベースのDIを適用するかを選択する事になります。&lt;br&gt;
&lt;br&gt;
疑問なのはここからです。&lt;br&gt;
&lt;br&gt;
外部ファイルベースのS2Container.NETでは起動時にDI対象のインスタンスがDIコンテナによってインスタンス生成・管理が行われますが、起動時にDIのセットアップが行われる為、起動時のレスポンス等懸念が出る場合があります。&lt;br&gt;
その反面、QuillではDI対象のオブジェクトが必要とされる場合にDIが適用される為、起動時のレスポンスをある程度排除する事が出来ます。&lt;br&gt;
ですが、属性ベースのDI考え方は、「ステートレスな依存性の場合」とされてますが、ステートレス時のDI適用の場面ってどんな場面なのかが分かりません。&lt;br&gt;
&lt;br&gt;
属性ベースでのDIの場合、インターフェイスと実装クラスが「１対１」という関係を作り、インターフェイスに実装クラスを指定する属性を指定します。&lt;br&gt;
&lt;br&gt;
&lt;div class="codename"&gt;IShoutLogic&lt;br&gt;（属性指定によるDI）&lt;/div&gt;
&lt;div class="code"&gt;
&lt;div style="font-family: メイリオ; font-size: 8pt; color: black; background: white;"&gt;
&amp;lt;Implementation(&lt;span style="color: blue;"&gt;GetType&lt;/span&gt;(HardShoutLogic))&amp;gt; _
&lt;br&gt;&lt;span style="color: blue;"&gt;Public&lt;/span&gt; &lt;span style="color: blue;"&gt;Interface&lt;/span&gt; IShoutLogic
&lt;br&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; &lt;span style="color: blue;"&gt;Function&lt;/span&gt; GetShoutString() &lt;span style="color: blue;"&gt;As&lt;/span&gt; &lt;span style="color: blue;"&gt;String&lt;/span&gt;
&lt;br&gt;&lt;span style="color: blue;"&gt;End&lt;/span&gt; &lt;span style="color: blue;"&gt;Interface&lt;/span&gt;
&lt;/div&gt;
&lt;/div&gt;
&lt;br&gt;
この属性ベースのDI適用の場合、インターフェイスと実装クラスが「１対１」の関係とする必要がある為、この時点でインターフェイスの「必要性」が自分としては良く分かりません。&lt;br&gt;
&lt;br&gt;
仮に実装クラスを変更する場合、IShoutLogicインターフェイスの属性を変更する必要がありますし、Employeeクラス内で実装クラスのHardShoutLogicクラスを直接生成している場合と、属性ベースのDIを使用している場合のメリット、デメリットが良くわかりません。&lt;br&gt;
違うクラスではIShoutLogic実装クラスをファクトリクラスを使用して取得するような実装があったとしても、こっちではDI、あっちではファクトリクラスとするのも解りづらくなるし。&lt;br&gt;
&lt;br&gt;
DIの適用場面など、皆さんはどのようにしてらっしゃいますか？&lt;br&gt;&lt;img src ="http://blogs.wankuma.com/kzt/aggbug/167292.aspx" width = "1" height = "1" /&gt;</description></item></channel></rss>