Très récemment, je suis tombé sur l'API de réflexion et à ma surprise, nous pouvons accéder et même modifier les variables privées.Je essayé le code suivant et j'ai eu la sortie suivante. P> Variable is name and value is John
Variable is name and value is Sam
4 Réponses :
Oui, cela violait les concepts OO. Cependant, il ne casse aucun modèle de sécurité Java. Il peut être contrôlé par Java Security Manager si nécessaire. La réflexion Java elle-même est une chose utile. Il est utilisé dans les annotations et les CIO qui sont des concepts très utiles avec la capacité de gérer des cours pendant l'exécution. p>
Vous ne pouvez pas mélanger La réflexion a un but totalement différent. Avec une réflexion, vous pouvez créer de manière dynamique des types et l'exécuter. Vous pouvez accéder aux membres de la classe de manière dynamique au moment de l'exécution. P>
Par exemple, j'ai récemment utilisé la réflexion pour exécuter des plugins code> code> dans mon application.ie J'ai chargé la DLL d'un répertoire particulier, puis a créé un objet de la classe par réflexion en la coulant dans un partagé Interface .. p> encapsulation code>,
polymorphisme code> avec réflexion. p>
L'API de réflexion ne modifie pas le but même de l'encapsulation de données? P> blockQuote>
oui et non. p>
- Oui, certaines utilisations de l'API de réflexion peuvent em> enfreindre l'encapsulation de données. LI>
- Non, pas toutes les utilisations de l'API de réflexion ne font pas l'encapsulation de données. En effet, un programmeur sage ne casse que l'encapsulation via l'API de réflexion lorsqu'il y a une bonne raison de le faire. Li>
- Non, l'API de réflexion ne change pas la but em> de l'encapsulation de données. Le but de l'encapsulation de données reste le même ... même si quelqu'un le brise volontairement. Li> ul>
Pourquoi devons-nous utiliser une API de réflexion? p> blockQuote>
Il y a beaucoup d'utilisations fortes> de réflexion que
ne pas forte> échecsulation de pause; par exemple. En utilisant la réflexion pour savoir quels types types une classe a, quelles annotations il a, quels membres il a, d'invoquer des méthodes et des constructeurs accessibles, de lire et de mettre à jour des champs accessibles, etc. P> et il y a des situations où est acceptable (à des degrés variables) à utiliser les variétés de casse d'encapsulation de réflexion: p>
Vous devrez peut-être regarder à l'intérieur d'un type encapsulé (par exemple Accès / modifier des champs privés) comme le moyen le plus simple (ou unique) pour mettre en œuvre certains tests d'unité. P> li>
Certaines formes d'injection de dépendance (AKA IOC), la sérialisation et la persistance impliquent et / ou mettent à jour des champs privés. P> li>
Très occasionnellement, vous devez casser l'encapsulation pour contourner un bogue dans une classe que vous ne pouvez pas réparer. p> li> ul>
J'ai lu dans certains sites qu'il peut être utilisé à des fins de test, mais selon moi, les modules sont testés et qui peuvent être effectués facilement à l'aide de cas de test Junit. Alors quelqu'un peut-il expliquer pourquoi avons-nous un tel piratage? P> blockQuote>
Cela dépend de la conception de votre classe. Une classe conçue pour être testable sera testable sans avoir à accéder à l'état "privé" ou exposera cet état (par exemple
protégé code> getters) pour permettre les tests. Si la classe ne le fait pas, un test JUNIT peut avoir besoin d'utiliser la réflexion pour regarder à l'intérieur de l'abstraction. P>
Ce n'est pas souhaitable (OMI), mais si vous écrivez des tests d'unité pour une classe que quelqu'un a écrit, et que vous ne pouvez pas "modifier" les API pour améliorer la testabilité, vous devrez peut-être choisir entre utiliser la réflexion ou non Tester du tout. P>
La ligne finale est que l'encapsulation de données est un idéal que nous nous efforçons de réaliser (en Java), mais il existe des situations où la chose correcte de manière pragmatique est de le casser ou de l'ignorer. P>
Notez que toutes les langues de l'OO ne supportent pas l'encapsulation de données solide comme Java. Par exemple, Python et JavaScript sont à la fois des langues de OO non privilégiées, mais les deux facilitent une classe d'accéder et de modifier l'état des objets d'une autre classe ... ou même changer le comportement des autres classes. L'abstraction de données forte n'est pas essentielle à la vue de chacun des moyens orientés objet. P>
L'API de réflexion ne change pas le but même des données Encapsulation? P>
Ne soyez pas trop raccroché sur les règles. Il y a des moments où il est utile de les casser. P>
Réflexation est très utile. Prenons par exemple mon code pour la journalisation de la recherche de modifications afin que je puisse leur connecter à une base de données: p>
xxx pré> C'est beaucoup plus facile de le faire de cette façon. Si j'utilisais des getters, je devrais écrire une méthode séparée pour chaque classe et modifier chaque fois qu'un nouveau champ a été ajouté. Avec réflexion, je peux simplement écrire une méthode pour gérer toutes mes classes. J'écris sur ma méthode de journal de journalisation ici P> blockQuote>
L'un des utilitaires de l'API de réflexion est le modèle du CIO, permettant au cadre d'appeler des méthodes inconnues à sa compilation (du cadre). Autre utilisation consiste à inspecter des classes pour effectuer des transformations (v.g., générer des réponses SOAP ou JSON directement à partir de haricots)
Dans votre code, vous n'avez pas eu à utiliser
fs.setapessable (true); code> parce que vous changez de champ privé dans une autre méthode de la même classe (qui ont accès à chaque domaine, même privé). J'ai changé votre exemple un peu pour montrer que, avec réflexion, vous pouvez accéder à des champs privés dans des endroits où il ne serait normalement pas possible.