您如何决定是使用库还是编写自己的实现

时间:2009-08-05 23:23:45

标签: coding-style

this question的启发,它开始是无辜的,但正在变成一场重大的火焰战争。

假设您需要一种实用方法 - 相当简单,但不是单行。引用的问题是如何重复X次字符串。您如何决定是使用第三方实现还是编写自己的实现?

第三方方法的明显缺点是您正在为代码添加依赖项。 但是如果你自己编写,你需要对它进行编码,测试它,(也许)对它进行描述,这样你最终可能会花更多的时间。

我知道决定本身是主观的,但你用来达到它的标准不应该是。

那么,您使用什么标准来决定何时编写自己的代码?

7 个答案:

答案 0 :(得分:18)

一般决定

在决定使用什么之前,我将创建一个库必须满足的标准列表。这可能包括大小,简单性,集成点,速度,问题复杂性,依赖性,外部约束和许可证。根据具体情况,决策所涉及的因素会有所不同。

通常,在编写自己的实现之前,我会寻找一个解决问题的合适库。如果我必须自己编写,我会阅读适当的算法并从其他实现中寻找想法(例如,使用不同的语言)。

如果在完成下面描述的所有方面后,我找不到合适的库或源代码,并且我已搜索(并在合适的论坛上询问),那么我将开发自己的实现。

<强>复杂性

如果任务相对简单(例如,MultiValueMap类),则:

  1. 查找现有的开源实现。
  2. 整合代码。
  3. 重写它,或者如果它过度则将其修剪下来。
  4. 如果任务很复杂(例如,灵活的面向对象的图形库),那么:

    1. 找一个编译(开箱即用)的开源实现。
    2. 执行“Hello,world!”等效。
    3. 根据需要执行任何其他评估。
    4. 根据问题域标准确定其适用性。
    5. <强>速度

      如果库太慢,那么:

      1. 简介。
      2. 优化它。
      3. 将结果反馈给社区。

        如果代码太复杂而无法优化,速度是一个因素,请与社区讨论并提供分析详细信息。否则,寻找一个等效但速度更快(可能更少功能丰富)的库。

        <强> API

        如果API不简单,那么:

        • 写一个门面并将其贡献给社区。
        • 或者找一个更简单的API。

        <强>尺寸

        如果编译的库太大,那么:

        • 仅编译必要的源文件。
        • 或者找一个较小的图书馆。

        <强>错误

        如果库没有开箱即用,请寻找替代方案。

        <强>依赖关系

        如果图书馆依赖于外部图书馆的分数,请寻找替代方案。

        <强>文档

        如果没有足够的文档(例如,用户手册,安装指南,示例,源代码注释),请寻找替代方案。

        时间限制

        如果有足够的时间找到最佳解决方案,那么就这样做。通常没有足够的时间从头开始编写。通常会有许多类似的库来评估。请记住,通过细致的松耦合,您可以随时将一个库换成另一个库。找到最初有效的方法,如果以后成为负担,则替换它。

        开发环境

        如果图书馆与特定的开发环境相关联,请寻找替代方案。

        <强>许可证

        Open source

答案 1 :(得分:6)

10个问题......

+++(使用库)...... ---(编写自己的库)

  1. 图书馆正是我需要的吗?可以通过几个步骤进行定制? +++
  2. 它是否提供几乎所有功能?容易扩展? +++
  3. 没时间? +++
  4. 一半好,和其他人一起玩得好? ++
  5. 难以扩展,但优秀的文档? ++
  6. 难以扩展,但大部分功能? +
  7. 功能还好,但过时了? -
  8. 功能好,但是很奇怪(疯狂的界面,不健壮,......)? -
  9. 图书馆工作,但需要决定的人处于hybris的状态? ---
  10. 图书馆工作,可管理的代码大小,投资组合需求更新? ---
  11. 有些想法......

    如果它是小而有用的东西,也可能对其他人来说,那么为什么现在写一个库并把它放在网上。发布这种小型图书馆的成本下降,以及其他人调整的障碍(见bitbucketgithub)。那么标准是什么?

    也许它不应该完全复制现有的已知库。如果它复制了现有的东西,它应该从新的角度解决问题,或者更好的是它应该提供更短或更精简的*解决方案。

    * <子> /乐趣

答案 2 :(得分:4)

如果它是一个微不足道的功能,那么就不值得拉入整个库。

如果它是一个非平凡的功能,那么它可能是值得的。

如果它的多个功能都可以通过拉入一个库来处理,那几乎绝对值得。

答案 3 :(得分:2)

保持平衡

你应该保持平衡的几个标准。我会考虑几个主题并提出几个问题。

开发时间VS维护时间

我可以在几个小时内完成我需要的东西吗?如果是,为什么我需要一个图书馆?如果我得到一个lib,我确定它不会花费数小时来调试和文档阅读?答案 - 如果我需要一些明显而直截了当的东西,我就不需要一个额外灵活的库。

简单VS灵活性

如果我只需要一个错误包装器,我需要一个具有灵活类型和堆栈跟踪和彩色打印的库....不...使用设计精美但灵活多用的库可能会降低代码速度。如果您打算使用2%的功能,则不需要它。

挖掘任务VS小任务

我是否面临着巨大的任务,我需要外部代码来解决它?绝对是AMQP或SQL操作是从头开始开发的太大的任务,但微小的日志记录可以在适当的地方解决。不要使用外部库来解决小任务。

我自己的libs VS外部库

有时候发展自己的图书馆会更好,因为它是100%使用的,100%适合你的目标,你知道它最好,它总是与你的应用程序保持同步。 不要构建自己的lib只是为了很酷,并记住你的供应商目录中的很多lib开发“只是为了酷”。

答案 4 :(得分:1)

对我来说,这将是一个相当简单的答案。

如果您需要具有成本效益,那么最好尝试找到一个能够满足您需求的库/框架。如果你找不到它,那么你将被迫写它或找到一个不同的方法。

如果你有时间并且觉得它很有趣,那就写一个。您将在此过程中学到很多东西,并且可以使用新的代码包来回馈开源社区。如果你不这样做,那就不要了。但如果你找不到一个,那么无论如何你必须写它;)

就个人而言,如果我可以证明写一个图书馆,我总是选择这个。这很有趣,你可以学到很多关于你所关注的内容,并且你还有另外一个工具可以添加到你的武器库并放上你的简历。

答案 5 :(得分:1)

如果功能只是应用程序的一小部分,或者如果您的需求与其他人的需求相同,那么库可能就是您的选择。例如,如果您需要使用和输出JSON,您可以在五分钟内将所有内容组合在一起以满足您的即时需求。但后来你开始一点一点地加入它。最后,你拥有在任何库中都可以找到的所有功能,但是1)你必须自己编写它们2)它不像你在库中找到的那样强大而且很好。

如果功能是应用程序的重要组成部分,并且如果您的需求与其他人的需求不完全相同,那么请仔细考虑。例如,如果您正在进行机器学习,您可能会考虑使用像Weka或Mahout这样的软件包,但这些是两种非常不同的动物,这个组件很可能是您应用程序的重要组成部分。在这种情况下,库可能是一个障碍,因为您的需求可能不符合原作者的设计参数,如果您尝试修改它,您将需要担心一个比您最小的更大,更复杂的系统会自己建立。

有一篇很好的文章讨论过清理HTML,以及它是如何成为应用程序的重要部分,以及需要大量调整的内容,所以使用外部库并不是最好的解决方案,尽管事实上,有许多图书馆完全按照要求做了。

答案 6 :(得分:0)

另一个考虑因素是安全性。

如果黑帽黑客在您的代码中发现错误,则可以创建漏洞利用并出售该漏洞。该库越受欢迎,利用价值就越大。考虑一下OpenSSL或Wordpress漏洞。如果重新实现代码,则您的代码很可能不会像流行库一样容易受到攻击。而且,如果您的lib不受欢迎,那么对代码进行零日漏洞利用可能就不值得了,而且很有可能您的代码不会被赏金猎人所针对。

另一个考虑因素是语言安全。 C语言可以非常快。但是从安全角度来看,这是自找麻烦。如果您使用某种脚本语言重新实现该lib,则任意代码执行利用的可能性很小(只要您知道可能的攻击媒介,例如序列化或评估)。