73 votes

Pourquoi C # n'autorise pas les fonctions non membres comme C ++

C# ne permettra pas à écrire non des fonctions de membre et de chaque méthode doit être une partie d'une classe. Je pensais à cela comme une restriction dans toutes les CLI langues. Mais j'ai eu tort et j'ai trouvé que le C++/CLI soutient les fonctions de membre. Lorsqu'il est compilé, le compilateur va faire de la méthode en tant que membre de certains sans nom de la classe.

Voici ce que le C++/CLI standard dit,

[Note: les fonctions de membre sont traités par la CLI en tant que membres de certains sans nom de la classe; toutefois, en C++/CLI code source, ces fonctions ne peuvent pas être qualifiés de manière explicite avec un nom de classe. la note de fin]

Le codage de la non-fonctions de membre dans les métadonnées n'est pas spécifié. [Note: Cela ne cause pas de problèmes d'interopérabilité, car ces fonctions ne peuvent avoir une visibilité publique. la note de fin]

Donc ma question est pourquoi ne pas C# mettre en place quelque chose comme ça? Ou pensez-vous qu'il ne devrait pas être non-fonctions de membre et de chaque méthode doit appartenir à une classe?

Mon avis est non-membre de la fonction de soutien et aide à éviter la pollution de la classe de l'interface.

Toutes les pensées..?

88voto

41voto

jalf Points 142628

C# n'a pas permis car Java ne le permettaient pas.

Je peux penser à plusieurs raisons pourquoi les concepteurs de Java n'a probablement pas le laisser

  • Java a été conçu pour être simple. Ils ont tenté de faire une langue sans les raccourcis aléatoires, de sorte que vous devez généralement juste un moyen simple de tout faire, même si d'autres approches auraient été plus propre ou plus concis. Ils veulent réduire la courbe d'apprentissage, et l'apprentissage "d'une classe peut contenir des méthodes" plus simple "d'une classe peut contenir les méthodes et les fonctions peuvent exister en dehors des classes".
  • Superficiellement, il semble de moins orientée objet. (Tout ce qui n'est pas partie d'un objet ne peuvent évidemment pas être orientée objet? Peut-il? bien sûr, C++, dit oui, mais le C++ n'était pas impliqué dans cette décision)

Comme je l'ai déjà dit dans les commentaires, je pense que c'est une bonne question, et il ya beaucoup de cas où des non-fonctions de membre aurait été préférable. (cette partie est surtout une réponse à toutes les autres réponses en disant: "vous n'en avez pas besoin")

En C++, où le non-fonctions membres sont autorisés, ils sont souvent privilégiées, pour plusieurs raisons:

  • Il contribue à l'encapsulation. Les moins de méthodes ont accès aux membres privés d'une classe, le plus facile que la classe sera de revoir ou de les maintenir. L'Encapsulation est une partie importante de la programmation orientée objet.
  • Le Code peut être réutilisé beaucoup plus facile quand il ne fait pas partie d'une classe. Par exemple, le C++ de la bibliothèque standard définit std::find ou std::sort` en tant que non-membre de fonctions, de sorte qu'ils peuvent être réutilisés sur tout type de séquences, si c'est des tableaux, des jeux, des listes liées, ou (pour les std::find, au moins) des flux. La réutilisation de Code est également une partie importante de la programmation orientée objet.
  • Il nous apporte un meilleur découplage. L' find fonction n'a pas besoin de savoir à propos de la classe LinkedList afin d'être en mesure de travailler sur elle. Si elle avait été définie comme une fonction membre, il serait un membre de la classe LinkedList, fondamentalement, la fusion des deux concepts dans une grosse goutte.
  • L'extensibilité. Si vous acceptez que l'interface d'une classe n'est pas seulement "l'ensemble de ses membres publics", mais aussi "tous les non-membres fonctions qui opèrent sur la classe", il devient alors possible d'étendre l'interface d'une classe sans avoir à modifier ou même de recompiler la classe elle-même.

La capacité à avoir des fonctions de membre peut avoir commencé avec le C (où vous n'aviez pas d'autre choix), mais en C++ moderne, il est une caractéristique essentielle dans son propre droit, et pas seulement pour l'arrière pour des fins de comparabilité, mais en raison de la plus simple, plus propre et plus de code réutilisable.

En fait, C#, semble avoir atteint un peu les mêmes choses, beaucoup plus tard. Pourquoi pensez-vous que les méthodes d'extension ont été ajoutés? Ils sont une tentative dans le sens de ce qui précède, tout en préservant la simple Java syntaxe. Les Lambdas sont également des exemples intéressants, comme ils sont aussi essentiellement de petites fonctions définies librement, non pas comme membres d'une catégorie donnée. Alors oui, le concept de non-fonctions de membre est utile, et C#'s les concepteurs ont réalisé la même chose. Ils ont juste essayé de se faufiler le concept par la porte arrière.

http://www.ddj.com/cpp/184401197 et http://www.gotw.ca/publications/mill02.htm deux articles écrits en C++ des experts sur le sujet.

14voto

Nemanja Trifunovic Points 17239

Les fonctions non membres sont une bonne chose car elles améliorent l’encapsulation et réduisent le couplage entre types. La plupart des langages de programmation modernes tels que Haskell et F # prennent en charge des fonctions libres.

9voto

Jon Skeet Points 692016

Quel est l'avantage de ne pas mettre de chaque méthode dans une classe nommée? Pourquoi un non-membre de la fonction de "polluer" la classe de l'interface? Si vous ne voulez pas cela comme une partie de l'API publique de la classe, soit ne pas la rendre publique ou de ne pas la mettre dans cette classe. Vous pouvez toujours créer une classe différente.

Je ne me souviens jamais vouloir écrire une méthode flottant autour sans portée - autres que les fonctions anonymes, bien sûr (qui ne sont pas vraiment les mêmes).

En bref, je ne vois pas d'avantages en situation de non-fonctions de membre, mais je peux voir les avantages en termes de cohérence, de nommage et de la documentation afin de mettre toutes les méthodes en conséquence d'une classe nommée.

3voto

Yuliy Points 8854
  • Avoir tout le code dans les classes permet un ensemble plus puissant de capacités de réflexion.
  • Il permet l'utilisation d'initialisateurs statiques, qui peuvent initialiser les données nécessaires aux méthodes statiques d'une classe.
  • Il évite les conflits de noms entre les méthodes en les incluant explicitement dans une unité à laquelle aucune autre unité de compilation ne peut ajouter.

Prograide.com

Prograide est une communauté de développeurs qui cherche à élargir la connaissance de la programmation au-delà de l'anglais.
Pour cela nous avons les plus grands doutes résolus en français et vous pouvez aussi poser vos propres questions ou résoudre celles des autres.

Powered by:

X