我正在尝试制作API。我只想隐藏最终程序员的所有细节。我还想为他们提供一些调用函数的选项。例如
我有4个具有相同名称但签名不同的功能(重载功能)
function1()
function1(arg1)
function1(arg1,arg2)
function1(arg1,arg2,arg3)
在上面的序列中,第4个函数即function1(arg1,arg2,arg3)
具有实际逻辑。 rest函数使用一些默认值调用next函数。
现在,如果用户在上面的序列中调用第一个函数,即function1()
,那么它正在调用第二个函数,即function1(arg1)
,其中包含一些默认值。等等。
我的问题是,这种链接可以节省LOC(代码行)并增加理解。但是,根据绩效观点,它是否合适?
我的条件
虽然您可以建议我使用其他语言表现,但前提是您没有建议“可变数量的参数”功能。
答案 0 :(得分:1)
在像C / C ++这样的语言中,编译器可以以一种可能没有性能损失的方式处理这些事情。在像Matlab这样的语言中,每个函数调用都有一个显着的时间。
如果这样的时间很重要,则很大程度上取决于你的方法被调用的频率。如果他们做了需要大量计算的事情,或者如果他们用于初始化,他们可能不经常被调用。在这些情况下,我不担心这一点。如果经常打电话,我会建议在做出决定之前进行衡量。
答案 1 :(得分:1)
通常,调用函数会导致内存跳转,这与性能相比仅比按顺序运行更昂贵。当这几次调用时,这不是一个大问题,即使有很多级别的链接。但是如果在大型循环中调用它,则可能是明显的性能问题。
注意:强>
要将链接减少到最小,您可以直接调用所有简化函数中最详细的函数(声明所有参数)。
function1(){
function1(null,null,null);
}
function1(arg1){
function1(arg1,null,null);
}
function1(arg1,arg2){
function1(arg1,arg2,null);
}
function1(arg1,arg2,arg3){
// Actual logic here...
}
这样你只需要一个额外的步骤。
注意:强>
编译器可能会通过优化调用为您提供一些优势。甚至可能是编译器会通过调用function1()
来取代对function1(null,null,null)
的初始调用,因为这都是function1()
所做的。
答案 2 :(得分:0)
[注意:我假设您在提出问题时谈论的是一种现代编程语言(因为它没有用语言明确标记)。如果不是这样,请放弃这个答案。]
首先,这种链接的目的是不,不应该减少LOC。代码行在性能方面是最不重要的,在某种程度上甚至是可读性,特别是在现代IDE的时代。 (对于记录:“在某种程度上”。我不说2500线方法是好的)
目的是避免重复逻辑,并为程序员提供便利,否则这将成为维护的噩梦。 (如果你将在所有方法中使用逻辑)并为最终程序员带来一些困难(如果你只有一个实现)
在现代编程语言中,由额外的两个方法类引起的开销是不可忽略的。这种优化(减少方法调用的数量)通常无处可去。
性能取决于方法的作用,如果存在任何性能问题,应该集中精力。
我没有看到任何问题,包括性能,并且实际上看到了您在问题中提到的那种链接方式的好处。
答案 3 :(得分:0)
用于在C中使用类似的内容,其中额外参数在未提供时始终为默认值。
要做到这一点,我使用了#define ...也许不是很漂亮,但是它可以工作,并且不会对最终的二进制文件产生任何性能影响(没有额外的堆栈空间,或者在程序计数器周围跳跃的时间)。
答案 4 :(得分:0)
可能这会有更糟的性能,但会增加更多的灵活性,并避免用户混淆参数。如果您执行以下操作,则可以使用类似于C ++中的默认参数:
public class function1 {
private String arg1 = "ding";
private String arg2 = "dong";
private String arg3 = "dang";
public function1 arg1(String arg1) {
this.arg1 = arg1;
return this;
}
public function1 arg2(String arg2) {
this.arg2 = arg2;
return this;
}
public function1 arg3(String arg3) {
this.arg3 = arg3;
return this;
}
public String eval() {
return arg1 + arg2 + arg3;
}
}
System.out.println(new function1().arg2("deng").eval());
这可能在这里有点过分,但随着你的争论越来越多,这就更好了。请注意,如果某些参数是必需的,则可以将它们放在构造函数中。