我有一个类MyClass
,它在实现中有一个错误。该类是库的一部分,因此我无法更改类的实现,因为它将默默地更改现有客户端的行为(在这种情况下可能依赖于该错误的客户端:例如,参见{{3} }))
我需要创建同一个类的第二个版本,其中包含错误修复。
我以前见过这样的情况,但我看到的命名总是增量Eg MyClass2
,MyClass3
。
这些案例可能非常罕见,但是我想知道是否有更好的方法来命名这些"版本化#34;类。
我想象一个解决方案,它会随着时间的推移而增长,并且具有这些类型的多个类,这些类可能会让人感到非常困惑,尤其是对于库而我想我必须在MyClass
,MyClassV2
,MyClassV3
等之间进行选择。
答案 0 :(得分:9)
在理想的世界中,新版本会引入额外的功能,同时仍然保持与以前版本的API 100%向后兼容。不幸的是,理想世界仍然是难以捉摸的,并不总是能够保持完全向后兼容性。在这种情况下,版本化后缀是合适的模式。
标准.NET命名约定是使用增量编号,如Class
,Class2
,Class3
等。这来自COM接口的命名约定,专为精确设计您正在描述的用例。例如,IHTMLDocument
界面目前有8个版本,从IHTMLDocument
到IHTMLDocument8
。
Cwalina和Abrams的原始Framework Design Guidelines书明确地推荐了这种做法,作者有这样的说法:
DO 使用数字后缀来指示现有API的新版本,如果API的现有名称是唯一有意义的名称(即,它是行业标准),并且添加任何有意义的后缀(或更改名称)都不是合适的选择。
// old API [Obsolete("This type is obsolete. Please use the new version of the same class, X509Certificate2."] public class X509Certificate { ... } // new API public class X509Certificate2 { ... }
原始Windows团队遵循的旧约定是将后缀Ex
添加到API的新增和改进版本中,该版本来自单词" extend。"但是,这并不能很好地扩展,导致函数混淆地加上后缀ExEx
。我不认为有ExExEx
;每个人都害怕接触这些API。 框架设计指南明确建议反对这种做法,那些接下来构建.NET的人已经吸取了教训:
不要使用" Ex" (或类似的)标识符的后缀,以区别于同一API的早期版本。
[Obsolete("This type is obsolete. ..."] public class Car { ... } // new API public class CarEx { ... } // the wrong way public class CarNew { ... } // the wrong way public class Car2 { ... } // the right way public class Automobile { ... } // the right way
显然,正如他们最后一个代码示例提示的那样,如果您要在新版本的API中添加对特定功能的支持,那么最好使用引用命名新类/接口该特定功能。
虽然上面几乎只关注类和接口,但同样的逻辑适用于该类的任何成员函数,可能会在以后的版本中添加。原始函数可以保留其原始名称,新添加的函数具有不同的名称,可以反映其迭代或其添加的功能。
答案 1 :(得分:4)
我想知道是否有更好的方法来命名这些“版本化”类。
“修复其他类中的错误的类”没有.NET命名约定。我会建议你工作场所的其他开发人员,看看他们是否有任何公司约定。我认为一致性比实际名称更重要。
在你的问题的旁注上,我根本不会创建一个新课程。我将使用DeprecatedAttribute
标记该方法并在同一个类中实现逻辑,公开一组新的API方法,这些方法已正确记录,以说明它们在此作为修复。您的库的客户可能已经熟悉MyClass
,这样做可以简化它们的使用,并且每次都要问自己“我应该使用哪个版本”。
答案 2 :(得分:3)
我会将现有类的所有行为复制到新类,重命名原始类以指示类已过时,将新类重命名为之前的实际名称并标记原始类(使用新名称)现在)作为[Obsolete]
表示不应再使用它。因此,所有消费代码都会自动调用新行为。因此,具有正确行为的新类将获取原始类的名称,例如,错误的类获取版本号。
对于遗留代码,您可以执行相反的操作,使用新名称创建一个新类,并将旧标记标记为Obsolete
。我知道带有版本号的SDK,其中最后一个数字表示该类的最新版本,其他所有版本都有这样的属性以及文档中的通知,提到该类已被新版本取代。
答案 3 :(得分:0)
答案 4 :(得分:0)
为清楚起见,如果发生这种情况,我会使用ClassV2.
这表明它是该类的另一个版本。