Question

OK, je sais ce que vous pensez, « pourquoi écrire une méthode que vous ne voulez pas que les gens utilisent ? » Droite?

Eh bien, en bref, j'ai une classe qui doit être sérialisée en XML.Pour que le XmlSerializer pour faire sa magie, la classe doit avoir un constructeur vide par défaut :

public class MyClass
{
  public MyClass()
  {
    // required for xml serialization
  }
}

Donc, j'en ai besoin, mais je ne veux pas que les gens le fassent. utiliser c'est ca existe-t-il un attribut qui peut être utilisé pour marquer la méthode comme « NE PAS UTILISER » ?

Je pensais utiliser le Obsolète attribut (puisque cela peut arrêter la construction), mais cela semble un peu "faux", existe-t-il un autre moyen de le faire, ou dois-je aller de l'avant et mordre la balle ?:)

Mise à jour

OK, j'ai accepté la réponse de Keith, car je suppose qu'au fond de mon cœur, je suis totalement d'accord.C'est pour cela que j'ai posé la question en premier lieu, je n'aime pas l'idée d'avoir le Obsolète attribut.

Cependant...

est toujours un problème, pendant que nous sommes avertis dans Intellisense, idéalement, nous aimerions interrompre la construction, alors y a-t-il un moyen de le faire ?Peut-être créer un attribut personnalisé ?

Une question plus ciblée a été créée ici.

Était-ce utile?

La solution

Si une classe est [Serialisable] (c'est à dire.il peut être copié partout selon les besoins) le constructeur sans paramètre est nécessaire pour désérialiser.

Je suppose que vous souhaitez forcer l'accès de votre code à transmettre les valeurs par défaut de vos propriétés à un constructeur paramétré.

En gros, vous dites que c'est OK pour le XmlSerializer pour faire une copie, puis définir les propriétés, mais vous ne voulez pas que votre propre code le fasse.

Dans une certaine mesure, je pense que c'est une conception excessive.

Ajoutez simplement des commentaires XML qui détaillent quelles propriétés doivent être initialisées (et quoi).

Ne pas utiliser [Obsolete], parce que ce n'est pas le cas.Réservez cela aux méthodes véritablement obsolètes.

Autres conseils

Vous pouvez utiliser:

[System.ComponentModel.EditorBrowsable(System.ComponentModel.EditorBrowsableState.Never)]

afin qu'il n'apparaisse pas dans Intellisence.Si le consommateur souhaite toujours l'utiliser, il le peut, mais il ne sera pas aussi détectable.

Le point de Keith sur l'ingénierie excessive est toujours d'actualité.

J'ai lu le titre et j'ai immédiatement pensé "attribut obsolète".Que diriez-vous

    /// <summary>
    /// do not use
    /// </summary>
    /// <param name="item">don't pass it anything -- you shouldn't use it.</param>
    /// <returns>nothing - you shouldn't use it</returns>
    public bool Include(T item) { 
    ....

En fait, je serais enclin à être en désaccord avec tous ceux qui préconisent l'utilisation du ObsoleteAttribute comme le dit la documentation MSDN :

Marquer un élément comme obsolète informe les utilisateurs que l'élément sera supprimé dans les futures versions du produit.

Étant donné que les constructeurs génériques pour la sérialisation XML ne doivent pas être supprimés de l'application, je ne les appliquerais pas au cas où un développeur de maintenance ultérieur ne serait pas familier avec le fonctionnement de la sérialisation XML.

En fait, j'utilise celui de Keith méthode consistant simplement à noter que le constructeur est utilisé pour la sérialisation dans la documentation XML afin qu'il apparaisse dans Intellisense.

Vous pourriez construire le vôtre Attribute classe dérivée, disons NonCallableAttribute pour qualifier les méthodes, puis ajoutez à votre tâche d'analyse de code build/CI la vérification pour surveiller si un code utilise ces méthodes.

À mon avis, vous ne pouvez vraiment pas forcer les développeurs à ne pas utiliser la méthode, mais vous pouvez détecter dès que possible quand quelqu'un a enfreint la règle et y remédier.

Wow, ce problème me dérange aussi.

Vous avez également besoin de constructeurs par défaut pour NHibernate, mais je souhaite forcer les gens à NE PAS utiliser les initialiseurs d'objets C# 3.0 afin que les classes passent par le code du constructeur.

throw new ISaidDoNotUseException();

Séparez votre objet sérialisable de votre objet de domaine.

Ce que vous recherchez, c'est le ObsoleteAttribute classe:

using System;

public sealed class App {
   static void Main() {      
      // The line below causes the compiler to issue a warning:
      // 'App.SomeDeprecatedMethod()' is obsolete: 'Do not call this method.'
      SomeDeprecatedMethod();
   }

   // The method below is marked with the ObsoleteAttribute. 
   // Any code that attempts to call this method will get a warning.
   [Obsolete("Do not call this method.")]
   private static void SomeDeprecatedMethod() { }
}

ObsoleteAttribute fonctionnera probablement dans votre situation - vous pouvez même provoquer l'arrêt de la construction si cette méthode est utilisée.

Étant donné que des avertissements obsolètes se produisent au moment de la compilation et que la réflexion nécessaire à la sérialisation se produit au moment de l'exécution, marquer cette méthode comme obsolète n'interrompra pas la sérialisation, mais avertira les développeurs que la méthode n'est pas là pour être utilisée.

j'utilise le ObsoleteAttribute.

Mais vous pouvez aussi bien sûr avoir quelques commentaires.

Et enfin, supprimez-le complètement si vous le pouvez (vous n'avez pas besoin de maintenir la compatibilité avec quelque chose d'ancien).C'est la meilleure façon.

Oui, il y en a.

J'ai écrit ce billet de blog à ce sujet Travailler avec le designer.

Et voici le code :


public class MyClass
{
  [Obsolete("reason", true)]
  public MyClass()
  {
    // required for xml serialization
  }
}

Licencié sous: CC-BY-SA avec attribution
Non affilié à StackOverflow
scroll top