では、公式文書、をクリックしてCore
コアパッケージと、それを開いて、あなたは、開口部の章では、約であることを見つけることができIoC
た容器。したがって、最初に理解してくださいIoC
。いつものように、Baiduエントリから開始します。
制御の反転(
Inversion of Control
、と略記IoC
)は、オブジェクト指向プログラミングの設計原則であり、コンピューターコード間の結合度を減らすために使用できます。最も一般的な方法は依存性注入(Dependency Injection
略してDI
)と呼ばれ、別の方法は「依存性ルックアップ」(Dependency Lookup
)と呼ばれます。制御の反転により、オブジェクトが作成されると、システム内のすべてのオブジェクトを規制する外部エンティティが、依存するオブジェクトの参照を渡します。依存関係がオブジェクトに注入されているとも言えます。パターンはファクトリパターンの昇華と見なす
ことができIoC
、IoC
コンテナは大きなファクトリと見なすことができますが、この大きなファクトリで生成されるオブジェクトはすべてXML
ファイルで定義されています。Java
「リフレクション」プログラミングを使用して、対応するオブジェクトがXMLで指定されたクラス定義に従って生成されます。実装の観点から、以前はファクトリモードでデッドに書き込まれていたオブジェクトは、IoC
構成XMLファイルに変更されます。これにより、ファクトリと生成されるオブジェクトが分離され、柔軟性と保守性が大幅に向上します。IoC
真ん中の最も基本的なJava
テクノロジーは「リフレクション」プログラミングです。素人の用語では、リフレクションは、指定されたクラス名(文字列)に基づいてオブジェクトを生成することです。このプログラミング方法により、アプリケーションは実行時に生成するオブジェクトを動的に決定できます。
言い換えれば、これIoC
はプログラミングのアイデアであり、主にコード間の結合を減らすために使用されます。具体的には、オブジェクトを作成するときに、クラシックnew
を使用してオブジェクトを作成する必要はありませんが、リフレクションをxml
ファクトリオブジェクトとプロダクションオブジェクトの分離と組み合わせて使用することで、柔軟性が向上します。
以前のweb
プロジェクト開発では、通常、次の実装を記述します。
- Dao、DaoImpl
- Service、ServiceImpl
- …
:複数の実装がある場合にデータをロードするには、我々のような継承特定のインターフェース、ことを複数実装クラスを記述する必要がある場合には、ある
dao
層UserDao
とUserDaoImpl
、それぞれ、二つのクラス:
public interface UserDao {
String getUserName();
}
public class UserDaoImpl implements UserDao {
@Override
public String getUserName() {
return "User!";
}
}
次に、service
2つのクラスUserService
とUserServiceImpl
2つのクラスをそれぞれ含むレイヤーを作成できます。内容は次のとおりです。
public interface UserService {
void getUserName();
}
public class UserServiceImpl implements UserService{
UserDao userDao = new UserDaoImpl();
@Override
public void getUserName() {
System.out.println(userDao.getUserName());
}
}
次に、次のようなテストクラスを作成します。
class UserServiceImplTest {
UserService userService = new UserServiceImpl();
@Test
void getUserName() {
userService.getUserName();
}
}
プロジェクトは次のように構成されています。
テスト結果:
上記は単純な呼び出しであり、問題はないようですが、私たちのDao
レベルでは、時間の複数の実現がある場合ServiceImpl
、Dao
実装で対応するものを変更する必要があります。基になるデータソーススイッチ。明らかに、開発のニーズに動的に適応させることはできません。
解決策:set
動的に設定するために使用する
public class UserServiceImpl implements UserService{
UserDao userDao;
// 动态注入
public void setUserDao(UserDao dao){
this.userDao = dao;
}
@Override
public void getUserName() {
System.out.println(userDao.getUserName());
}
}
// 此时的测试类
class UserServiceImplTest {
UserService userService = new UserServiceImpl();
@Test
void getUserName() {
((UserServiceImpl)userService).setUserDao(new UserDaoImpl());
userService.getUserName();
}
}
このようにして、基盤となるデータソースの変更を動的に設定することが可能になり、顧客サービスのニーズや動的な変更に簡単に適応できます。
ここに考えがあります:基礎となるデータソースの元のイニシアチブはプログラマーの手にありますが、現在のset
インジェクション方法では、イニシアチブは呼び出す必要のある人の手にあり、他の人がどのメソッドを呼び出すことができるようになります彼らが必要とする。この種の考え方は、制御の反転です。