代码之家  ›  专栏  ›  技术社区  ›  Mohamad

干燥是否意味着应用程序性能更好?

  •  2
  • Mohamad  · 技术社区  · 16 年前

    我反复被告知在编程时不要重复自己。我遇到一个场景,我想知道是写两个函数,每个函数都有特定的用途,还是一个函数同时处理这两个用途。我不确定什么是“最佳实践”方法:

    所有涉及的函数都允许一个人将列表项的排名更改一个位置,加或减一。所有项及其列组都保存在MySQL数据库表中。)

    两个功能 一个函数将一个项目的等级一个一个地上移,另一个函数将等级一个地下移。

    一个函数

    在性能方面,编写两个函数并让它们分担负载是否更好?如果同一个函数正在接收大量请求,是否存在“函数重载”这样的情况?

    我认为这与此无关,但我使用的是ColdFusion,另外的“direction”参数将是一个字符串,该字符串包装在一个语句中,该语句检查其值以确定要采取的操作。

    8 回复  |  直到 16 年前
        1
  •  5
  •   Larry Lustig    16 年前

    不,DRY并不一定意味着你的应用程序会有更好的性能。它成功了 更容易的 编写一个性能良好的应用程序(因为优化只需要在一个地方完成),它几乎肯定会使您的应用程序更易于维护。但理论上,非干燥应用程序的性能与干燥应用程序一样好。

    选择写一个更一般的函数或两个更具体的函数并不一定是干的事情。您必须平衡这两个函数中有多少代码是相同的,多少是不同的,而不是通用函数的额外复杂性。在我看来,这是一个边界情况,但当我做了它,我做了一个通用函数。

    编程中有一个术语“函数重载”,但它的含义与您的建议大不相同。经常调用一个函数不会有“过分强调”它的风险。

        2
  •  3
  •   mqp    16 年前

    通常情况正好相反;更多的重用,更多的抽象层意味着在微观层次上,你的程序正在做更多的工作(除非你有一个非常聪明的编译器或优化器在两者之间)。消除DRY的一些小例子通常被现代编译器和运行时弄得毫无意义,它们是循环展开和函数内联。

    然而,限制抽象所带来的任何微小收益通常都是由编写一个由可重用的部分组成的组织良好的程序所带来的可读性和灵活性方面的巨大收益所支配的。

        3
  •  2
  •   Thorbjørn Ravn Andersen    16 年前

    优点在于需要更改旧代码的维护部分。如果在多个地方重复相同的代码,则不修复所有这些地方的风险很高。

    不同的 功能。

    关于您对“重载”函数调用次数过多的担心。不是那样的。CPU不关心代码是否在一个或两个函数中,只要设计是纯的,并且代码尊重并行程序的语义(这本身就很有挑战性)。

        4
  •  2
  •   Pekka    16 年前

    DRY用于创建更小、更易于维护的代码。

    从性能的角度来看,这种差异在大多数场景中实际上是不存在的。在编译语言中,编译器将优化可能存在的任何性能差异。

        5
  •  2
  •   Daniel DiPaolo    16 年前

    DRY(不要重复你自己)原则并不是真正的目标是最大化性能,尽管坚持它可以使优化更容易获得更好的性能。DRY的目标是简化代码,使其更精简、更易于维护。

    在实践中,这可能意味着性能的提高,因为一旦你找到了一种最佳的方法来做某件事,你就可以在你写它的地方,在它使用的任何地方实现它,这都会获得好处。

        6
  •  2
  •   Montagist    16 年前

    与许多其他编程方法(或缩写,或模式,或其他)一样,您的方法应该是实用的,因为没有一种方法总是等同于“性能更好”的应用程序。从我的头顶上,我会说你可能会以空间的形式实现名义上的储蓄,但可能不会到你会注意到或改变的程度。

    然而,归根结底,DRY的主要观点是,性能更好的开发人员比性能更好的应用程序更需要性能更好的开发人员。如果需要进行优化,那么只有一个地方可以进行优化,而不必记住所有你“重复自己”的地方:

        7
  •  2
  •   Andy Lester    16 年前

    DRY是关于编写正确的代码,无论是现在还是将来。

    如果你的代码被破坏了,它有多快并不重要。

        8
  •  1
  •   steinar Justin CI    16 年前

    更新: 更新以答复对此答复的评论。这是对一般问题的一个回答,因为DRY并不会自动导致性能更好的应用程序,尽管这里提到的成本实际上很少。

    Debug/Window/Disassembly 窗口打开:

    class Program
    {
        static void Main(string[] args)
        {
            Do();
            Do2();
            Console.ReadKey();
        }        
    
        private static void Do()
        {
            int a = 10;
            a = a + 10;
            a = a * 10;
            Console.WriteLine(a);
        }
    
        private static void Do2()
        {
            int a = 10;
            Add(ref a);
            Mult(ref a);
            Console.WriteLine(a);
        }
    
        private static void Add(ref int a)
        {
            a = a + 10;
        }
    
        private static void Mult(ref int a)
        {
            a = a * 10;
        }
    }
    

    在反汇编窗口中,您将看到应用程序要调用的实际语句 Do 和 Do2 . Do2号 模拟 枯燥的节目。如果您逐步浏览程序集代码,您会注意到每个函数顶部有一个类似于以下内容的部分:

    00000000  push        ebp 
    00000001  mov         ebp,esp 
    00000003  push        eax 
    00000004  mov         dword ptr [ebp-4],ecx 
    00000007  mov         eax,dword ptr ds:[71D81468h] 
    0000000d  cmp         dword ptr [eax],0 
    00000010  je          00000017 
    00000012  call        FFFFDD68 
    00000017  nop 
    

    这是开销的一部分,只在Do()中发生一次。除此之外,总会有一个操作将控制流定向到内存中的另一个位置。

    话虽如此,我绝对建议在任何情况下都使用干的。

    推荐文章