我可以互换使用这些术语,并且通常遵循我听到的最流行的方式,或者在当前对话中最近调用它的方式,例如“复制交换成语”和“单例模式”。
我能想出的最大区别是几乎要按字面意思复制的代码通常称为模式,而要按字面意思理解的代码通常称为idiom,但这甚至并不总是正确的。这似乎只是一种风格或流行语的差异。这是否符合您对如何使用这些术语的看法?有语义上的区别吗?
我可以互换使用这些术语,并且通常遵循我听到的最流行的方式,或者在当前对话中最近调用它的方式,例如“复制交换成语”和“单例模式”。
我能想出的最大区别是几乎要按字面意思复制的代码通常称为模式,而要按字面意思理解的代码通常称为idiom,但这甚至并不总是正确的。这似乎只是一种风格或流行语的差异。这是否符合您对如何使用这些术语的看法?有语义上的区别吗?
习语是特定于语言的。
模式是独立于语言的设计原则,通常以“模式语言”(统一模板)编写,描述诸如激励环境、优缺点、相关模式等内容。
当人们从 On High (分析师、顾问、学者、方法论大师等)观察程序开发时,看到开发人员在各种情况和环境中一遍又一遍地做同样的事情,那么从观察中获得的情报可以提炼成一个模式。模式是一种使用代表通用抽象的软件工具“做事”的方式。
一些例子:
OO 编程将全局变量从开发人员手中夺走。对于那些他们确实仍然需要全局变量但需要一种方法来使它们的使用看起来干净且面向对象的情况,有单例模式。
有时您需要创建一个具有多种可能不同类型之一的新对象,具体取决于某些情况。一种丑陋的方式可能涉及不断扩大的case
陈述。以 OO 干净的方式实现这一目标的公认“优雅”方式是通过“工厂”或“工厂方法”模式。
有时,很多开发人员都以某种方式做事,但这是一种不好的方式,不应该被推荐。这可以在反模式中形式化。
模式是一种高级的做事方式,并且大多数与语言无关。无论您使用模式创建对象new Object
还是Object.new
无关紧要。
由于模式有点理论和正式,因此通常有一个正式的模式(嘿 - 单词重载!让我们说“模板”)来描述它们。这样的模板可能包括:
习语是低级的东西,通常在语言级别上运行。例子:
*dst++ = *src++
在 C 中,将数据元素从 复制src
到 ,dst
同时增加指向两者的指针;它通常在一个循环中完成。显然,您不会在 Java 或 Object Pascal 中看到这个习语。
while <INFILE> { print chomp; }
是(从内存中粗略引用的)一个 Perl 习惯用法,用于循环输入文件并打印出文件中的所有行。该语句中有很多隐式变量使用。同样,除了在 Perl 中,您不会在任何地方看到这种特殊的语法。但是一位老 Perl 黑客会快速查看该声明并立即识别您在做什么。
与模式与语言无关的观点相反,Paul Graham和Peter Norvig都认为需要使用模式是您的语言缺少功能的标志。(访客模式经常被挑出来作为这方面最明显的例子。)
我通常认为“模式”和“成语”之间的主要区别在于大小。成语是一些小东西,比如“为保存集合的变量类型使用接口”,而模式往往更大。我认为习语的小规模确实意味着它们更多地是特定于语言的(我刚刚给出的示例是 Java 习语),但我不认为这是它们的定义特征。
因为如果你把 5 个程序员放在一个房间里,他们可能甚至不会就什么是模式达成一致,所以这个问题没有真正的“正确答案”。
我曾经听过并且非常喜欢的一种观点(尽管我一生都无法回忆起来源),即习语可能应该是你的语言,或者有一些语言有它们。相反,它们是我们使用的技巧,因为我们的语言没有为它们提供直接的原语。例如,Java 中没有单例,但我们可以通过隐藏构造函数并提供 getInstance 方法来模仿它。
另一方面,模式与语言无关(尽管它们通常指的是特定的范式)。您可能有一些基础设施来支持它们(例如,用于 MVC 的 Spring),但它们不是,也不会是语言构造,但是您可能需要该范式中的任何语言的它们。