什么是垫片?


Answers:


92

从维基百科:

在计算机编程中,填充程序是一个小型库,可以透明地拦截API,更改传递的参数,处理操作本身或将操作重定向到其他地方。通常,当API的行为发生变化时就会产生垫片,从而导致仍依赖于旧功能的旧应用程序出现兼容性问题。在这些情况下,较旧的API仍可以由较新的代码之上的瘦兼容性层支持。Shims还可以用于在与开发目的不同的软件平台上运行程序。


82
这个答案与在维基百科上进行实际的Google搜索没有什么不同。一个例子会很好。
dance2die '16

4
这听起来像是使用Facade设计模式来连接库。
blz

84

根据维基百科的定义,术语“垫片”在技术上会根据其定义归类为“结构”设计模式。面向对象的软件设计模式(有些人会说是事实上的)参考了“设计模式,可重用的面向对象软件的元素”(也被称为“四人之帮”),很清楚地描述了许多类型的“结构”设计模式。

“四人帮”文本轮廓至少3点很好地建立的模式被称为“代理”,“适配器”和“正面”,这都提供了“垫片”类型的功能。在大多数领域中,对于相同的根概念,经常会使用或忽略使用不同的首字母缩略词,这会引起人们的困惑。使用“垫片”一词来描述更具体的“结构”设计模式“代理”“适配器”“门面”无疑是这种情况的一个明显例子。“垫片”只是“结构”模式“代理”,“适配器”,“门面”以及其他可能类型的更具体类型的更笼统的术语。


5
这个答案表明,填充片是一种设计模式(是多个设计模式中的一种),并命名了一些类似的设计模式,并且与人们如何因使用不同的首字母缩略词而感到困惑。但是它实际上并没有回答垫片是什么,它是做什么或如何使用的原始问题。
Richie Thomas

53

通过卡通简单说明

垫片的示例:

我的狗拉尔夫(My Dog Ralph)是一位幸运的混蛋(意为双关语)

摘要

注意:这个比喻很紧张。通常Ralph会得到他所要求的确切信息-但是如何获得它的机制是他可能不会想到的。

填充程序是一些代码,它负责处理所要求的内容(“拦截”),而没有人对此有任何理智。这是一般概念。现在,您应该能够阅读和理解有关垫片的Wikipedia条目。


13

至于单词的起源,请引用Apple的Dictionary小部件

noun
   a washer or thin strip of material used to align parts, 
   make them fit, or reduce wear.

verb ( shimmed, shimming) [ trans. ]
   wedge (something) or fill up (a space) with a shim.

ORIGIN early 18th cent.: of unknown origin

这似乎与网页设计师如何使用该术语非常吻合。



12

根据Microsoft的文章“揭开垫片的神秘面纱”

这是一个基于英语单词shim的隐喻,shim是一个工程术语,用于描述插在两个对象之间的一块木头或金属,以使它们更好地结合在一起。在计算机编程中,填充程序是一个小型库,可以透明地拦截API,更改传递的参数,处理操作本身或将操作重定向到其他地方。Shims还可以用于在与开发目的不同的软件平台上运行程序。

我将其解释为,垫片是任何充当中间人并部分或完全改变程序的行为或操作的代码库的通用术语。像真正的中间人一样,它可能会影响传递给该程序的数据,或影响从该程序返回的数据。

本文以Windows API为例,发现以下相关句子:

应用程序通常不知道请求将发送到填充DLL而不是Windows本身,Windows也不知道请求来自其他来源而不是应用程序(因为填充DLL只是应用程序进程中的另一个DLL) 。

为了概括此报价,使“垫片三明治”成为“面包”的两个程序应该无法区分是与对方程序交谈还是与垫片交谈。

使用垫片的利弊有哪些?

再次,从文章:

您可以在不访问源代码或根本不更改它们的情况下修复应用程序。您只需付出最少的额外管理开销即可,而且您可以通过这种方式修复相当数量的应用程序。缺点是支持,因为大多数供应商不支持填充程序。您不能使用垫片来修复每个应用程序。对于供应商停业的应用程序,软件的战略性不足以使其无法获得支持,或者只是想花点时间,大多数人通常会考虑使用垫片。

在这个问题的上下文中,在阅读了以上链接之后,“代理”,“适配器”和“外观”等术语更有意义(至少对我而言)。


3

正如我们在此处的许多回复中所看到的,填充程序是一种适配器,它提供API级别的功能,而不一定是该API的一部分。该线程有很多良好而完整的响应,因此我不会进一步扩展定义。

但是,我想我可以添加一个很好的示例,它是Javascript ES5 Shim(https://github.com/es-shims/es5-shim):

在过去的几年中,Java语言发展了很多,并且在语言规范的许多其他变化中,许多新方法已添加到其核心对象中。

例如,在ES2015规范(又名ES5)中,该方法find已添加到Array原型中。因此,假设您正在使用此规范之前的JavasScript引擎(例如:Node 0.12)运行代码,而该引擎尚未提供该方法。通过加载ES5填充程序,这些新方法将被添加到Array原型中,即使您没有在较新的JavaScript规范上运行,也可以使用它们。

您可能会问:为什么有人会这样做而不是将环境升级到较新版本(例如,节点8)?

在很多实际案例中,这种方法都有意义。一个很好的例子:

假设您有一个在旧环境中运行的旧系统,并且需要使用这种新方法来实现/修复功能。环境的升级仍在进行中,因为存在兼容性问题,需要进行大量代码更改和测试(关键组件)。

在此示例中,您可以尝试构建自己的此类功能版本,但这会使您的代码更难阅读,更复杂,可能引入新的错误,并且需要大量的额外测试才能覆盖您所知道的功能。在下一个版本中可用。

取而代之的是,您可以使用此填充程序并利用这些新方法,这是利用了该修补程序/功能在升级后将兼容的事实,因为您已经在使用下一个规范中已知的方法。还有一个额外的理由:由于这些方法是下一语言规范的本机,因此很有可能它们的运行速度比尝试制作自己的版本时可能执行的任何实现都要快。

欢迎使用这种方法的另一个真实场景是在浏览器级别。假设您需要支持旧版浏览器,并想利用这些新功能。Javascript是一种语言,它允许您在其核心对象中添加/修改方法(例如向Array原型添加方法),并且那些填充程序库足够聪明,只有在当前实现缺少此类方法时,才可以添加此类方法。

PS:1)您将看到与这些Javascript垫片相关的术语“填充”。Polyfill是一种更特殊的垫片,用于在不同浏览器级别的规范中提供向前兼容性。顺便说一句,我上面的示例正是指这样的示例。

2)垫片不限于此示例(添加了将来版本中将可用的功能)。也有不同的用例也被认为是垫片。

3)如果您对如何实现这种特定的polyfill感到好奇,则可以打开Javascript Array.find规范并滚动到页面的末尾,您将在其中找到该方法的规范实现。


0

SHIM是对所有服务执行的另一级安全检查,以保护上游系统。SHIM Server使用标头用户凭证来验证每个传入的请求,并对照在请求中传递的用户凭证(SOAP / RESTFUL)。

By using our site, you acknowledge that you have read and understand our Cookie Policy and Privacy Policy.
Licensed under cc by-sa 3.0 with attribution required.