热门标签 | HotTags
当前位置:  开发笔记 > 编程语言 > 正文

变量而不是类调用-variablesasopposedtoclasscalls

Ihaverecentlylearnedthatifyouhaveareferencetoaclassasafunctionparameter,itisbette

I have recently learned that if you have a reference to a class as a function parameter, it is better practice and more efficient to store certain needed pieces of information as local variables rather than accessing the classes members every time you need them in the function.

我最近了解到,如果你有一个类作为函数参数的引用,那么将某些所需的信息作为局部变量存储,而不是每次在函数中需要时访问类成员都是更好的实践和更有效的方法。

so...

void function(const Sphere& s)
{
    //lots of calls to s.centre and s.radius
}

or

void function(const Sphere& s)
{
    Vector3 centre = s.centre; float radius = s.radius;
    //an equal amount of calls to centre and radius
}

I am told the second is better, but why? And also, where is a good place to start researching this more fully? (for dummys please!)

我被告知第二个更好,但为什么?而且,哪里有一个开始更充分地研究这个的好地方? (请给dummys!)

6 个解决方案

#1


9  

Whoever told you this probably thought that the second version was likely to be faster.

谁告诉你这可能认为第二个版本可能会更快。

I think this is bad advice, for two reasons:

我认为这是一个糟糕的建议,原因有两个:

  1. It may or may not actually be faster. This depends on the compiler, on what exactly the code is doing etc.
  2. 实际上可能会或可能不会更快。这取决于编译器,代码究竟在做什么等等。

  3. Even if it is faster, this screams premature optimization. One should micro-optimize only after profiling the code and establishing which part of the code is the overall bottleneck.
  4. 即使它更快,这也会过早地优化。只有在分析代码并确定代码的哪一部分是整体瓶颈之后,才应进行微优化。

#2


8  

The concept is intuitive, but wrong. The concept is that accessing members takes more calculations than local variables, so by converting members to variables, you save performance.

这个概念很直观,但错了。概念是访问成员比局部变量需要更多的计算,因此通过将成员转换为变量,可以节省性能。

But this is wrong. Your compiler will optimize this in ways you could never imagine. Don't attempt to be smarter than the compiler.

但这是错误的。您的编译器将以您无法想象的方式优化它。不要试图比编译器更聪明。

#3


6  

This could actively be dangerous. If s.centre or s.radius change during the execution of this function (say due to a function you call or another thread), you will end up with two inconsistent, old values in your local variables -- causing bugs. Even if you're doing this safely, why take the chances of introducing bugs when you can just refer back to the canonical variables themselves?

这可能会非常危险。如果s.centre或s.radius在执行此函数期间发生更改(比如由于您调用的函数或其他线程),您最终会在本地变量中出现两个不一致的旧值 - 导致错误。即使您正在安全地执行此操作,为什么在您可以回溯到规范变量本身时,还有机会引入错误?

#4


5  

You were lied to. Moreover, you should not be worrying about such minutiae unless you have profiled your code and found this to be a main source of inefficiency in your code. Don't try to outsmart your compiler's optimizer. It is better at optimizing your code than you are.

你被骗了。此外,除非您对代码进行了分析并发现这是代码中效率低下的主要原因,否则您不应该担心这种细节。不要试图超越编译器的优化器。优化代码比使用它更好。

#5


2  

Here is a general outlook of your code:

以下是您的代码的一般展望:

void function(Sphere s)
{
    Vector3 centre = s.centre; float radius = s.radius;
    //an equal amount of calls to centre and radius
}

First off, you'd gain much more efficiency by passing Sphere as a const reference. This way, a new copy isn't created, which is probably more expensive than member access. So the way to go is:

首先,通过将Sphere作为const引用传递,您将获得更高的效率。这样,不会创建新副本,这可能比成员访问更昂贵。所以要走的路是:

void function(const Sphere& s)
{
    Vector3 centre = s.centre; float radius = s.radius;
    //an equal amount of calls to centre and radius
}

Secondly, you shouldn't access members of classes directly. It may be easy now, but in a large project it's really hard to debug. You should use inline getters and setters. That way, the generated code is the same, but you have a single entry point.

其次,您不应该直接访问类的成员。现在可能很容易,但在大型项目中,调试真的很难。您应该使用内联getter和setter。这样,生成的代码是相同的,但您只有一个入口点。

Thirdly, this version isn't thread safe. What if a different thread changes s? s.center and s.radius would change, but you'd still be operating on the old values.

第三,这个版本不是线程安全的。如果另一个线程改变了怎么办? s.center和s.radius会改变,但你仍然会使用旧值。

Lastly, compilers do a better job at optimizing than you can, so it's better to leave this one up to the compiler.

最后,编译器在优化方面做得比你做得更好,所以最好把这个放到编译器上。

#6


0  

Whoever told you that is wrong. You can improve performance by using inline functions. Also in your example use

谁告诉你这是错的。您可以使用内联函数来提高性能。另外在你的例子中使用

void function(Sphere &s) 

Saves using the copy constructor.

使用复制构造函数保存。


推荐阅读
  • Python正则表达式学习记录及常用方法
    本文记录了学习Python正则表达式的过程,介绍了re模块的常用方法re.search,并解释了rawstring的作用。正则表达式是一种方便检查字符串匹配模式的工具,通过本文的学习可以掌握Python中使用正则表达式的基本方法。 ... [详细]
  • IjustinheritedsomewebpageswhichusesMooTools.IneverusedMooTools.NowIneedtoaddsomef ... [详细]
  • 本文整理了315道Python基础题目及答案,帮助读者检验学习成果。文章介绍了学习Python的途径、Python与其他编程语言的对比、解释型和编译型编程语言的简述、Python解释器的种类和特点、位和字节的关系、以及至少5个PEP8规范。对于想要检验自己学习成果的读者,这些题目将是一个不错的选择。请注意,答案在视频中,本文不提供答案。 ... [详细]
  • 微软头条实习生分享深度学习自学指南
    本文介绍了一位微软头条实习生自学深度学习的经验分享,包括学习资源推荐、重要基础知识的学习要点等。作者强调了学好Python和数学基础的重要性,并提供了一些建议。 ... [详细]
  • 生成式对抗网络模型综述摘要生成式对抗网络模型(GAN)是基于深度学习的一种强大的生成模型,可以应用于计算机视觉、自然语言处理、半监督学习等重要领域。生成式对抗网络 ... [详细]
  • 本文介绍了设计师伊振华受邀参与沈阳市智慧城市运行管理中心项目的整体设计,并以数字赋能和创新驱动高质量发展的理念,建设了集成、智慧、高效的一体化城市综合管理平台,促进了城市的数字化转型。该中心被称为当代城市的智能心脏,为沈阳市的智慧城市建设做出了重要贡献。 ... [详细]
  • 本文讨论了在Windows 8上安装gvim中插件时出现的错误加载问题。作者将EasyMotion插件放在了正确的位置,但加载时却出现了错误。作者提供了下载链接和之前放置插件的位置,并列出了出现的错误信息。 ... [详细]
  • CSS3选择器的使用方法详解,提高Web开发效率和精准度
    本文详细介绍了CSS3新增的选择器方法,包括属性选择器的使用。通过CSS3选择器,可以提高Web开发的效率和精准度,使得查找元素更加方便和快捷。同时,本文还对属性选择器的各种用法进行了详细解释,并给出了相应的代码示例。通过学习本文,读者可以更好地掌握CSS3选择器的使用方法,提升自己的Web开发能力。 ... [详细]
  • Android Studio Bumblebee | 2021.1.1(大黄蜂版本使用介绍)
    本文介绍了Android Studio Bumblebee | 2021.1.1(大黄蜂版本)的使用方法和相关知识,包括Gradle的介绍、设备管理器的配置、无线调试、新版本问题等内容。同时还提供了更新版本的下载地址和启动页面截图。 ... [详细]
  • sklearn数据集库中的常用数据集类型介绍
    本文介绍了sklearn数据集库中常用的数据集类型,包括玩具数据集和样本生成器。其中详细介绍了波士顿房价数据集,包含了波士顿506处房屋的13种不同特征以及房屋价格,适用于回归任务。 ... [详细]
  • 3.223.28周学习总结中的贪心作业收获及困惑
    本文是对3.223.28周学习总结中的贪心作业进行总结,作者在解题过程中参考了他人的代码,但前提是要先理解题目并有解题思路。作者分享了自己在贪心作业中的收获,同时提到了一道让他困惑的题目,即input details部分引发的疑惑。 ... [详细]
  • MyBatis多表查询与动态SQL使用
    本文介绍了MyBatis多表查询与动态SQL的使用方法,包括一对一查询和一对多查询。同时还介绍了动态SQL的使用,包括if标签、trim标签、where标签、set标签和foreach标签的用法。文章还提供了相关的配置信息和示例代码。 ... [详细]
  • 深度学习中的Vision Transformer (ViT)详解
    本文详细介绍了深度学习中的Vision Transformer (ViT)方法。首先介绍了相关工作和ViT的基本原理,包括图像块嵌入、可学习的嵌入、位置嵌入和Transformer编码器等。接着讨论了ViT的张量维度变化、归纳偏置与混合架构、微调及更高分辨率等方面。最后给出了实验结果和相关代码的链接。本文的研究表明,对于CV任务,直接应用纯Transformer架构于图像块序列是可行的,无需依赖于卷积网络。 ... [详细]
  • JDK源码学习之HashTable(附带面试题)的学习笔记
    本文介绍了JDK源码学习之HashTable(附带面试题)的学习笔记,包括HashTable的定义、数据类型、与HashMap的关系和区别。文章提供了干货,并附带了其他相关主题的学习笔记。 ... [详细]
  • Igotthiscode(IknowitsinSpanishIcantranslateifneeded)wheretheygivemethefunctionS ... [详细]
author-avatar
朱泊潇
这个家伙很懒,什么也没留下!
PHP1.CN | 中国最专业的PHP中文社区 | DevBox开发工具箱 | json解析格式化 |PHP资讯 | PHP教程 | 数据库技术 | 服务器技术 | 前端开发技术 | PHP框架 | 开发工具 | 在线工具
Copyright © 1998 - 2020 PHP1.CN. All Rights Reserved | 京公网安备 11010802041100号 | 京ICP备19059560号-4 | PHP1.CN 第一PHP社区 版权所有