Questions tagged «c++»

有关C ++的问题,C ++是一种静态类型,自由格式,多范式,已编译的通用编程语言。

10
C ++:二进制级别缺乏标准化
为什么ISO / ANSI没有在二进制级别上标准化C ++?C ++存在许多可移植性问题,这仅是由于缺乏二进制级别的标准化。 Don Box写道(引自他的《基本COM》一书,“ COM作为更好的C ++”一章) C ++和可移植性 一旦决定将C ++类作为DLL分发,就会面临C ++的基本弱点之一,即二进制级别的标准化不足。尽管ISO / ANSI C ++草案工作论文试图对将编译的程序以及运行它们的语义产生的影响进行编码,但它并未尝试标准化C ++的二进制运行时模型。第一次,当客户端尝试从C ++开发环境(而不是用于构建FastString DLL的环境)中链接FastString DLL的导入库时,此问题将首次显现。 还有更多的好处,或者由于缺少二进制标准化而损失了吗?
14 c++  dll  ansi  iso 

3
克里斯·索耶(Chris Sawyer)用汇编语言编写大多数过山车大亨将涉及多长时间以及哪种类型的复杂性?
关于这个问题,我还有另一个问题…… 克里斯·索耶(Chris Sawyer)用汇编语言编写大多数过山车大亨将涉及多长时间以及哪种类型的复杂性? 为了指定并分解这个问题,我感兴趣; 您估计克里斯大约要花多少工时(有一个猜测)?或者,换句话说,用C / C ++编写整个程序,给出近似的汇编程序编码小时数百分比。 熟悉汇编程序的程序员是否会认为这对于如此低级的语言抽象来说是一项过于复杂的任务?除了性能优势外,这还只是克里斯拥有的一种奇特的自然能力,还是值得学习的技能?我很感兴趣,如果人们认为复杂性/性能值得值得(为了编写)学习汇编程序,或者如果您在汇编程序方面有很多天生的技能(大概是通过使用硬件工作),那么这仅仅是“值得”吗? /硬件驱动程序/电子设备/等)。

3
我们应该在结构中添加构造函数吗?
我们经常使用c ++结构来定义数据结构,而不是使用类,类可以是带有成员方法的完整模块。从现在开始,我们知道它们都是相同的(松散地说)。 我们经常使用/处理结构作为仅数据实体的事实产生了这样的冲动,即我们也不要添加默认构造函数。但是构造函数总是很棒的,它们使事情变得更简单并有助于消除错误。 如果将默认构造函数添加到我的数据结构,会不会感到烦恼? 如果满足其他条件,实现默认构造函数还会使结构Non-POD(普通旧数据类型)吗? 为了正确理解,考虑一个简单的示例,但实际上结构会大得多。 struct method { char name[32]; float temperature; int duration; }; 每次我创建一个方法时,我都会担心(至少可以说)是否忘记设置一些值。想象一下,我忘记设置temperature该方法并将其应用于系统,该系统现在是一个随机的高值,并且会导致混乱。或者我忘了设置duration,现在该方法将其自身应用到未知的高持续时间。 为什么我应该负责每次都初始化对象,而不是执行保证它的构造函数?

2
Const C ++ DRY策略
为了避免与C ++ const无关的重复,在某些情况下const_cast可以工作,但返回非const的私有const函数不起作用? 在Scott Meyers的有效C ++项目3中,他建议将const_cast与静态强制转换结合使用可以是避免重复代码的有效且安全的方法,例如 const void* Bar::bar(int i) const { ... return variableResultingFromNonTrivialDotDotDotCode; } void* Bar::bar(int i) { return const_cast<void*>(static_cast<const Bar*>(this)->bar(i)); } Meyers继续解释说,让const函数调用非const函数是危险的。 下面的代码是一个反例,显示: 与Meyers的建议相反,有时将const_cast与静态强制转换结合使用是危险的 有时让const函数调用非const的危险性较小 有时两种使用const_cast的方式都可能隐藏有用的编译器错误 避免const_cast并让其他const私有成员返回非const是另一种选择 避免代码重复的const_cast策略中的一种是否被视为良好实践?您愿意使用私有方法策略吗?在某些情况下,const_cast可以工作,但私有方法不能工作吗?还有其他选择(除了重复)吗? 我对const_cast策略的担心是,即使编写时代码正确,以后在维护期间代码也可能变得不正确,并且const_cast将隐藏有用的编译器错误。似乎普通的私有功能通常更安全。 class Foo { public: Foo(const LongLived& constLongLived, LongLived& mutableLongLived) : mConstLongLived(constLongLived), mMutableLongLived(mutableLongLived) {} // case A: we shouldn't …
14 c++  dry  const 

4
为什么C ++不允许您使用构造函数的地址?
是否有某种特定的原因会在概念上破坏该语言,还是有某种特定的原因在某些情况下在技术上不可行? 用法将与新运算符一起使用。 编辑:我将放弃希望让我的“新操作员”和“新操作员”变得直截了当并保持直率。 问题的关键是:构造函数为何如此特殊?当然要记住,语言规范告诉我们什么是合法的,但不一定是道德的。合法的东西通常由与该语言其余部分在逻辑上一致的东西,简单明了的东西以及编译器可以实现的东西告知。标准委员会权衡这些因素的可能依据是经过深思熟虑的,因此很有趣。
14 c++ 

3
使用C / C ++宏作为条件编译的快捷方式是一种好习惯吗?
假设我要在代码中包含几种类型的输出消息。其中之一是DEBUG,仅当在Debug模式下编译代码时才打印。 通常我必须写一些像 #ifdef DEBUG std::cout << "Debug message" << std::endl; #endif 在许多地方使用起来非常麻烦和烦人。 为代码段定义宏是一种好习惯,这样您就可以使用它吗? MSG_DEBUG("Debug message") 还是有没有其他更优雅的方式在没有宏的情况下如何处理它?我对C和C ++中可能的解决方案感兴趣,因为我在不同的项目中使用了这两种语言。
13 c++  c  macros 

5
确保跨平台兼容性(C ++)的技术?
我正在完成我最早的C ++项目之一(根据框架),该项目应该是跨平台的。我完全在Windows和Visual Studio中开发了该项目,以为既然这些库都是跨平台的,那么“以后”进行OSX构建将是微不足道的。事实并非如此,而是“ Windows代码”无法正常运行,并且需要解决一些编译错误。 预先存在哪些技术可以确保代码与所有平台兼容?同时开发所有平台,从而在添加新功能时针对每个平台同时测试代码,而不是一个接一个地开发不同的平台版本?(*) 从外观上来看,特别建议不要依赖于工具,而可以使用“开发过程”来帮助跨平台兼容性,无论使用什么工具。就像上面的一个(*)。 具体来说,我正在使用WDL-OL(https://github.com/olilarkin/wdl-ol)和一些跨平台DSP库开发VST插件。WDL-OL项目同时设置了VS和Xcode项目,但我想问题出在库中,然后是编译器之间的差异。

1
对象生存期不变性与移动语义
很久以前,当我学习C ++时,我就强烈强调C ++的部分意思是就像循环具有“循环不变式”一样,类也具有与对象生命周期相关的不变式-应该是正确的只要物体还活着 应该由构造函数建立并由方法保留的事物。封装/访问控制可帮助您强制执行不变式。RAII是您可以使用此想法做的一件事。 从C ++ 11开始,我们现在有了移动语义。对于支持移动的类,从某个对象移动不会正式终止其生命周期,因为该移动应该使它处于某种“有效”状态。 在设计一个类时,如果将其设计为仅保留该类的不变性直到将其移出之前,是不好的做法吗?或者是说没关系,如果它可以让你让它走得更快。 具体来说,假设我有一个不可复制但可移动的资源类型,如下所示: class opaque { opaque(const opaque &) = delete; public: opaque(opaque &&); ... void mysterious(); void mysterious(int); void mysterious(std::vector<std::string>); }; 无论出于何种原因,我都需要为此对象创建一个可复制的包装,以便可以在某些现有的调度系统中使用它。 class copyable_opaque { std::shared_ptr<opaque> o_; copyable_opaque() = delete; public: explicit copyable_opaque(opaque _o) : o_(std::make_shared<opaque>(std::move(_o))) {} void operator()() { o_->mysterious(); } void …

3
在标准类型和用户定义类型之间进行语法区分的目的是什么?
尽管在这里我将特别提及C ++和Bjarne Stroustrup的命名约定,但原则上,我已经看到人们在这里和那里对其他语言使用一些相似的规则。 因此,基本思想是在阅读代码时应该能够将标准类型与用户定义的类型区分开。例如,Bjarne Stroustrup建议使用 类型(例如Square和Graph)的首字母大写 考虑到 C ++语言和标准库不使用大写字母 可以实现上述目标。 但是,为什么我们需要这样做呢?区分标准类型和用户定义类型的目的是什么? 在这件事上,我找不到Bjarne Stroustrup的任何推理,而且,我自己以截然相反的方式思考。:DI知道,我知道,“我要和谁争论Stroustrup?” 但是,听着,许多C ++语言功能(例如,运算符重载)用于允许用户定义类型的语法支持水平与标准类型相似。然后所有这一切都被另一个命名规则所困扰... PS更不用说一个单词常常不足以命名一个班级,而以大写字母开头的下划线分隔的单词看起来太陌生了。

5
Java堆分配比C ++更快
我已经在SO上发布了这个问题,它的确可以。不幸的是它关闭了(只需要一票就可以重新打开),但是有人建议我将它发布在这里,因为它更合适,因此以下内容实际上是该问题的粘贴内容 我正在阅读对此答案的评论,并且看到了这句话。 对象实例化和面向对象功能使用起来非常快(在许多情况下,它们比C ++更快),因为它们是从一开始就设计的。且收集速度很快。即使在大多数优化的C代码方面,标准Java在这一领域也优于标准C / C ++。 一位用户(我可能会添加非常高的代表)大胆地捍卫了这一主张,并指出 Java中的堆分配比C ++更好 并添加了该语句来捍卫Java中的集合 与Java集合相比,Java集合与C ++集合相比速度更快,这在很大程度上归因于内存子系统的不同。 所以我的问题是,这是否真的是真的,如果是的话,为什么Java的堆分配这么快?

8
我们应该坚持让一名员工在多年后仍在编写糟糕的代码吗?[关闭]
关闭。这个问题是题外话。它当前不接受答案。 想改善这个问题吗? 更新问题,以使它成为软件工程堆栈交换的主题。 6年前关闭。 我将这个问题提交给C ++程序员,因为:a)只有C ++程序员才能判断示例的技术优点;b)只有一个程序员才会有另一位这样编写代码的程序员的气质。 人力资源部和董事意识到存在问题仅仅是因为他们看到了现场的证据。我打电话给我们是否给问题程序员更多时间。许多错误都处于非常基本的水平上-我(对程序员)的问题是,是否应该根据自己当前代码的样本,对自称是高级C ++开发人员的人们是否会产生怀疑。非程序员-甚至是C ++编程以外的人-也无法对此做出任何判断。 作为背景知识,我被分配了为一家老牌公司管理开发人员的任务。他们只有一个开发人员,专门研究所有C ++编码(从此以后),但是工作质量却很糟糕。代码审查和测试发现了许多问题,最严重的问题之一是内存泄漏。开发人员从未测试过自己的代码是否泄漏,而且我发现应用程序在使用一分钟后可能会泄漏许多MB。用户正在报告巨大的速度下降,而他的看法是:“与我无关,如果他们退出并重新启动,那一切都很好。” 我给他提供了检测和跟踪泄漏的工具,并与他坐了许多小时,以演示如何使用这些工具,出现问题的位置以及如何解决这些问题。我们已经走了6个月了,我指定他编写一个新模块。在将其集成到更大的代码库中之前,我进行了审查,并且很沮丧地发现与以前相同的不良编码。我无法理解的部分是,某些编码比业余编码差。例如,他想要一个可以填充另一个类(Bar)的对象的类(Foo)。他决定Foo将保留对Bar的引用,例如: class Foo { public: Foo(Bar& bar) : m_bar(bar) {} private: Bar& m_bar; }; 但是(出于其他原因)他还需要Foo的默认构造函数,并且他没有质疑他的最初设计,而是写了这个gem: Foo::Foo() : m_bar(*(new Bar)) {} 因此,每次调用默认构造函数时,都会泄漏Bar。更糟的是,Foo从堆中为其他两个对象分配了内存,但他没有编写析构函数或复制构造函数。因此,每个Foo分配实际上都会泄漏3个不同的对象,您可以想象复制Foo时发生了什么。而且-只会变得更好-他在其他三个班级上重复了相同的模式,所以这不是一次过的失败。整个概念在很多层面上都是错误的。 如果这是一个新手,我会感到更多的理解。但是这个家伙已经这样做了很多年,并且在过去的几个月中一直非常专注于培训和建议。我知道他大部分时间在没有指导或同行评审的情况下工作,但我开始感到他无法改变。所以我的问题是,您会坚持与正在编写如此明显的不良代码的人吗?

2
如何避免在包装器中编写大量传递函数?
我有一个类,它包装了一个通用基本类型的另一个类。由于基本类型的接口很大,因此需要编写许多传递函数。我正在寻找避免这种情况的方法。 让我们举个例子: Car / \ Volvo VolvoWithTrailer 现在,我必须在VolvoWithTrailer的car接口中实现每个函数,并在包装​​好的Volvo对象上调用适当的函数,但GetMaxSpeed()可能会返回更低的值。基本上我将有很多功能,例如 int VolvoWithTrailer::GetNumSeats() { return mVolvo.GetNumSeats() } 解决此问题的一个明显方法是使VolvoWithTrailer成为Volvo的子类。 Car | Volvo | VolvoWithTrailer 但这似乎违反了主张组成优先于继承的原则。 我还要如何避免编写所有这些包装器(语言是C ++)?或者-如果那是您的职位-为什么我应该只写它们/只使用继承?有没有模板魔术可以帮助解决这个问题?

3
为什么编译器不能避免自己两次导入头文件?
C ++的新手!因此,我正在阅读以下内容:http : //www.learncpp.com/cpp-tutorial/110-a-first-look-at-the-preprocessor/ 护头板 因为头文件可以包含其他头文件,所以有可能最终导致头文件被多次包含的情况。 因此,我们制定了预处理程序指令来避免这种情况。但是我不确定-为什么编译器不能 ... 不能两次导入相同的东西? 鉴于标头保护符是可选的(但显然是一种很好的做法),几乎让我认为在某些情况下您确实想导入两次。尽管我根本无法想到任何这种情况。有任何想法吗?
13 c++  compiler 


3
使用模板时,如何处理越来越长的编译时间?
我使用Visual Studio 2012,在某些情况下,我们将模板参数添加到“ just”类中​​以引入“接缝点”,以便在单元测试中可以将这些部分替换为模拟对象。 您通常如何在C ++中引入接缝点:使用接口和/或通过使用模板参数,还基于某些条件与隐式接口进行混合?提出此问题的原因之一还在于,当有时编译单个C ++文件(包括模板文件,还可能包括其他模板)时,会导致在开发人员机器上生成大约5-10秒的目标文件。 。 据我所知,由于模板包含模型,VS编译器在编译模板方面也不是特别快(实际上,您在每个间接使用它的文件中都包含了模板的定义,并且每次修改时都可能重新实例化该模板)与模板无关的内容)(在进行增量编译时),编译时间可能会出现问题。 使用模板时,处理增量(且不仅是)编译时间的方法是什么(除了更好/更快的编译器:-)外)。
13 c++  tdd  templates 

By using our site, you acknowledge that you have read and understand our Cookie Policy and Privacy Policy.
Licensed under cc by-sa 3.0 with attribution required.