【问题标题】:Is `cd` being faster than `addpath` a motivation to use it?`cd` 比 `addpath` 快是使用它的动机吗?
【发布时间】:2013-08-17 21:42:38
【问题描述】:

我的一个answers 最近因建议使用cd(path_to_toolbox 而被否决,而不是path 工具之一,例如addpathrmpath。鉴于我收到的强烈批评,我必须想象使用path 工具有很好的理由,大概它们在某种程度上更健壮,尤其是当代码分发到其他系统时。

然后我决定记录cdaddpath 的性能,并惊讶地发现以下结果。在每次试验之前,我都清理了工作区并创建了一个带有交替路径的字符串数组:

clear
clc

p1 = 'c:\MATLAB7\toolbox\symbolic\@sym\';
p2 = matlabroot;

newpath = repmat(' ',100,100);

for ii=1:2:99
    newpath(ii,1:length(p1)) = p1;    
    newpath(ii+1,1:length(p2)) = p2;    
end

然后我运行addpathcd 如下:

tic
for ii=1:100
    addpath(newpath(ii,:))
end
toc

经过的时间是 13.437000 秒。

tic
for ii=1:100
    cd(newpath(ii,:))
end
toc

经过的时间是 1.078000 秒。

感谢任何关于是否存在使用 cd 的条件(例如设置函数(工具箱或其他)的路径)的条件。 虽然它可能是被认为草率,我已经使用cd 很多年了,虽然如果重复使用减速可能会很明显,但我发现如果它不在程序的高度迭代部分中使用,减速是值得的它为编码带来的简单性。值得注意的是,addpath 使用起来并不复杂,但现在我似乎有一个真正的理由更喜欢cd:它实际上更快。

编辑

作为这篇文章的附言,我恳求mea culpa 不正当使用cd(在本例中为addpath)。然而,在一种经常用于快速而肮脏的脚本编写的语言中,应该有这样的使用空间。应该记住,matlab 用户的专业知识是有等级的,在某些情况下,不那么“高级”和看似草率的编程技术实际上可以被解释为在短期内是有利的(如果不是长期的话,或版本和目录结构管理可能会出现问题的地方)。

作为附录,我包含一些指向 SO 上的帖子的链接,以及超出该地址的内置函数覆盖、阴影等,其中可以使用 addpath(我也认为 cd):

How to unhide an overriden function?

How to get a handle to an overriden built-in function?

How to wrap an already existing function with a new function of the same name

http://www.mathworks.in/matlabcentral/newsreader/view_thread/264354

【问题讨论】:

  • addpath 不需要你改变当前的matlab 目录,它把它添加到matlab 搜索路径中。假设您在几个不同的文件夹中有文件,那么每次您想使用另一个路径中的函数或类时,都必须更改当前的 matlab 目录……
  • 如果附加路径而不是默认前缀会发生什么?不过,您的比较确实很公平。关键是可以设置和保存路径,而每次都需要在脚本中调用cd(如果您想将用户返回到他们最后的pwd,则需要调用两次)。在某些情况下,cd-ing 可能会破坏内容并导致意外错误,例如,将使用用户 pwd 中的内容的函数传递给 cds 来回传递的主函数。
  • @horchler:你是不是漏掉了一个“NOT”(不公平的比较):)关于追加而不是前置的好点。
  • 版本管理也有问题。如果我将具有多个功能的整个程序复制到一个新目录,那么初始 cd 将完成与 addpath 一样多的工作,并且考虑到在这种情况下路径的无常性,任何选择似乎都可以 - 假设所有代码都复制到同一个目录水平。
  • @DennisJaheruddin:很好,MATLAB 也有 genpath 函数来生成文件夹及其所有子文件夹的路径字符串,与 addpath 一起使用

标签: cd matlab


【解决方案1】:

显然,随着path 变长,MATLAB 必须搜索更多位置来查找函数、脚本、类等。所以我想如果你有很长的时间,它会对性能产生负面影响path

另一方面,当前目录只是一个必须搜索的位置(当然要考虑优先顺序)。

另外,比较两者是不公平的,除非您可以将所有文件放在一个文件夹中。


请注意您的编码风格:您可以使用字符串元胞数组而不是字符矩阵来存储newpath

newpath = cell(100,1);
for i=1:100
    newpath{i} = '...';
end

【讨论】:

  • 关于性能的说明:MATLAB 通常会缓存路径上目录的信息。此外,为了检测文件系统中的更改并自动使用最新版本的 M 文件(无需显式重新散列),MATLAB 为文件系统中的更改通知注册处理程序(请参阅help changeNotification
  • 是的,但问题是基于速度(或其他)是否有理由使用cd 而不是path。如果我正确阅读了您的答案,那么(是?)并且没有理由让我在之前的问题上被否决。
  • 对于在循环中使用 i,我可能不赞成你:那是糟糕的编程风格 :>)
  • 不,我的意思是你的测试不是一个公平的比较。不断在文件夹之间跳转以使用位于不同位置的功能既不实用也不便携。 path 就是为此目的而设计的。
  • 我不确定该链接问题中的 OP 试图做什么,但我没有看到混乱的根源。如果你想要符号区分,你应该将x定义为一个符号变量(syms x),如果你想要数字差异,那么定义xx = 1:100)。除非我有误解,否则没有重叠,也没有必要与path 混淆。您会看到 MATLAB 根据第一个参数的类型分派函数调用,因此如果 x 是符号的,它将调用 @sym/diff,否则将调用常规的。请记住,fun(obj) 就像 obj.fun() 用于对象方法调用
【解决方案2】:

我认为如果你像这样使用cd在路径中添加一些东西,应该避免大多数缺点:

function addpathwithcd(pathToAdd)
currentPath = pwd;
cd(pathToAdd);
cd(currentPath);

但是,在进行(非常小的)测试之后,这对我来说似乎并不比简单地使用addpath(pathToAdd) 更快。

实际上这对我来说有点意外,因为您录制了 13 倍的速度差异,而我只使用了两次 CD,因此我预计会有 6 倍的速度差异。

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 2010-12-25
    • 2011-03-26
    • 2010-10-07
    • 2011-02-06
    • 2012-10-14
    • 2014-05-12
    • 2020-01-31
    • 1970-01-01
    相关资源
    最近更新 更多