小编Nic*_*rca的帖子

为什么f(i = -1,i = -1)未定义的行为?

我正在阅读有关评估违规的顺序,他们给出了一个令我困惑的例子.

1)如果标量对象的副作用相对于同一标量对象的另一个副作用未按顺序排列,则行为未定义.

// snip
f(i = -1, i = -1); // undefined behavior
Run Code Online (Sandbox Code Playgroud)

在这种情况下,i是一个标量对象,显然意味着

算术类型(3.9.1),枚举类型,指针类型,指向成员类型的指针(3.9.2),std :: nullptr_t和这些类型的cv限定版本(3.9.3)统称为标量类型.

在这种情况下,我不明白该陈述是如何含糊不清的.在我看来,无论第一个或第二个参数是否首先被评估,i最终都是-1,并且两个参数也是-1.

有人可以澄清一下吗?


UPDATE

我非常感谢所有的讨论.到目前为止,我非常喜欢@ harmic的答案,因为它暴露了定义这个陈述的陷阱和错综复杂,尽管它看起来有多么简单.@ acheong87指出了使用引用时出现的一些问题,但我认为这与这个问题的未测序副作用方面是正交的.


摘要

由于这个问题得到了很多关注,我将总结一下主要观点/答案.首先,请允许我进行一个小小的题外话,指出"为什么"可以具有密切相关但又略有不同的含义,即"为什么原因 ","为什么原因 "和"为了什么目的 ".我将根据他们所解决的"为什么"的含义分组答案.

为什么原因

这里的主要答案来自Paul Draper,Martin J提供了类似但不那么广泛的答案.Paul Draper的回答归结为

它是未定义的行为,因为它没有定义行为是什么.

答案在解释C++标准所说的内容方面总体上非常好.它还解决了UB的一些相关案例,如f(++i, ++i);f(i=1, i=-1);.在第一个相关案例中,不清楚第一个论点是否应该是i+1第二个i+2,反之亦然; 在第二个中,不清楚i函数调用后是否应为1或-1.这两种情况都是UB,因为它们属于以下规则:

如果相对于同一标量对象的另一个副作用,标量对象的副作用未被排序,则行为未定义.

因此,f(i=-1, i=-1)也是UB,因为它属于同一规则,尽管程序员的意图是(恕我直言)显而易见且毫不含糊.

Paul Draper在他的结论中也明确表示

可以定义行为吗?是.它被定义了吗?没有.

这让我们想到"为什么原因/目的是 …

c++ undefined-behavior language-lawyer

266
推荐指数
9
解决办法
2万
查看次数

使用CMake将资源(例如,着色器代码;图像)嵌入到可执行文件/库中

我正在用C++编写一个应用程序,它依赖于我项目中的各种资源.现在,我有从生成的可执行文件到我的源中硬编码的每个资源的相对路径,这允许我的程序打开文件并读入每个资源中的数据.这工作正常,但它要求我从相对于资源的特定路径启动可执行文件.因此,如果我尝试从其他任何地方启动我的可执行文件,它将无法打开文件而无法继续.

有没有一种可移植的方法让CMake将我的资源嵌入到可执行文件(或库)中,以便我可以在运行时只在内存中访问它们而不是打开路径脆弱的文件?我找到了一个相关的问题,看起来嵌入资源可以用一些ld魔法做得很好.所以我的问题是如何使用CMake 以便携,跨平台的方式做到这一点?我实际上需要在x86和ARM上运行我的应用程序.我只支持Linux(嵌入式),但如果有人可以建议如何为Windows(嵌入式)做这个,也可以获得奖励积分.

编辑:我忘了提到解决方案的理想属性.我希望能够在为ARM构建时使用CMake交叉编译应用程序,而不是必须在我的ARM目标上本地编译它.

c++ cmake cross-compiling embedded-resource

29
推荐指数
5
解决办法
2万
查看次数

map :: emplace()具有自定义值类型

我在使用时遇到了麻烦map::emplace().任何人都可以帮我找出正确的语法吗?我正在尝试做与此示例中相同的操作.这是我的版本:

#include <map>
using namespace std;

class Foo
{
  // private members

  public:
    Foo(int, char, char) /* :init(), members() */ {  }

    // no default ctor, copy ctor, move ctor, or assignment
    Foo() = delete;
    Foo(const Foo&) = delete;
    Foo(Foo &&) = delete;
    Foo & operator=(const Foo &) = delete;
    Foo & operator=(Foo &&) = delete;
};


int main()
{
  map<int, Foo> mymap;
  mymap.emplace(5, 5, 'a', 'b');

  return 0;
}
Run Code Online (Sandbox Code Playgroud)

根据GCC 4.7(带有-std=c++11标志),我emplace在线上错了. …

c++ gcc c++11 gcc4.7

20
推荐指数
1
解决办法
9053
查看次数

无法在当前目录中提供脚本

显然,source如果该脚本在当前目录中,我就不能使用脚本.例如,

# source some/dir/script.sh
Ok
Run Code Online (Sandbox Code Playgroud)

工作正常,但如果我和脚本在同一个目录中,则会出错:

# cd some/dir
# source script.sh
-sh: source: script.sh: file not found
Run Code Online (Sandbox Code Playgroud)

是什么赋予了?这是改变目录的唯一方法吗?

如果相关,我在Angstrom Linux上使用bash v4.2.10.

linux bash sh

9
推荐指数
1
解决办法
3434
查看次数

C++ 11时钟:g ++ steady_clock :: is_steady == false?

因此,准确的时间是对我很重要,我正在调查这3种类型的C++ 11,即指定的时钟system_clock,steady_clockhigh_resolution_clock.我最初关注的是测试不同类型时钟的呼叫开销是否存在差异,以及检查每种类型时钟的分辨率.这是我的示例程序:

#include <chrono>
#include <cstdio>
using namespace std;
using namespace std::chrono;

int main(int argc, char **argv)
{
  size_t N = 1e6;
  if(2 == argc) {
    sscanf(argv[1], "%zu", &N);
  }

#if defined(hrc)
  typedef high_resolution_clock clock;
#warning "High resolution clock"
#elif defined(sc)
  typedef steady_clock clock;
#warning "Steady clock"
#elif defined(sys)
  typedef system_clock clock;
#warning "System clock"
#endif

  const double resolution = double(clock::period::num) / double(clock::period::den);

  printf("clock::period: %lf us.\n", resolution*1e6);
  printf("clock::is_steady: %s\n", clock::is_steady ? "yes" : "no"); …
Run Code Online (Sandbox Code Playgroud)

c++ gcc c++11 gcc4.7

9
推荐指数
2
解决办法
4820
查看次数

我可以在派生类中为一个基类的成员设置别名吗?

说我有以下课程:

template <class T>
class Base {
  protected:
    T theT;
    // ...
};

class Derived : protected Base <int>, protected Base <float> {
  protected:
    // ...
    using theInt = Base<int>::theT;     // How do I accomplish this??
    using theFloat = Base<float>::theT; // How do I accomplish this??
};
Run Code Online (Sandbox Code Playgroud)

在我的派生类中,我想引用Base::theT一个更直观的名称,在Derived类中更有意义.我正在使用GCC 4.7,它具有很好的C++ 11功能.有没有办法使用一个using语句来完成我在上面的例子中尝试的这种方式?我知道在C++ 11中,using关键字可以用于别名类型以及例如.将受保护的基类成员带入公共范围.是否有类似的成员别名机制?

c++ c++11

8
推荐指数
1
解决办法
2320
查看次数

如何在Eigen3库中有效地提取复杂矩阵的实部/虚部?

我在Eigen3库中有一些复杂,密集的矢量/矩阵,我想将实部和虚部提取到单独的数组中.在Matlab中,我可以做类似的事情

cplxFoo = [1, 1i; -1i -1]
re = real(cplxFoo)
im = imag(cplxFoo)
Run Code Online (Sandbox Code Playgroud)

期望收益率

cplxFoo =
   1.0000 + 0.0000i   0.0000 + 1.0000i
   0.0000 - 1.0000i  -1.0000 + 0.0000i
re =
     1     0
     0    -1
im =
     0     1
    -1     0
Run Code Online (Sandbox Code Playgroud)

有喜欢什么real(),并imag()在Eigen3 Matlab的功能呢?

现在,我所知道的唯一可行的东西就是类似的东西

MatrixXcd cplxFoo = ...;
MatrixXd re(cplxFoo.rows(), cplxFoo.cols());
MatrixXd im(cplxFoo.rows(), cplxFoo.cols());

for(size_t j=0; j<cplxFoo.cols(); ++j) {
    for(size_t i=0; i<cplxFoo.rows(); ++i) {
        re(i, j) = cplxFoo(i,j).real();
        im(i, j) = cplxFoo(i,j).imag();
    }
}
Run Code Online (Sandbox Code Playgroud)

它工作,我甚至可以把它放在一个函数中,但后来我不得不做我自己的循环矢量化,展开等,而且我必须做一个额外的副本. …

c++ matlab eigen3

7
推荐指数
1
解决办法
7993
查看次数

你如何在MATLAB中关闭断言?

在调试我的MATLAB代码之后,我希望能够关闭断言以在可能的情况下获得一些额外的速度.(断言中的表达式非常简短快速,但是在紧密循环中有很多调用,所以它加起来.是的,我描述了.)我如何在MATLAB中全局地做到这一点?我正在寻找类似于NDEBUG在C/C++中定义,或在Python中启用优化或-disableassertions在Java中标记的东西.查找/替换assert(%assert(是对我的口味太丑陋了.

matlab assert

6
推荐指数
1
解决办法
1026
查看次数

如何将数字数据读取为uint8_t

我有一些人类可读的数字数据istream.值范围从0到255,我想存储它们uint8_t.不幸的是,如果我尝试类似的东西

uint8_t a, b;
stringstream data("124 67");
data >> a >> b;
Run Code Online (Sandbox Code Playgroud)

然后我最终a == '1'b == '2'.我知道这是许多情况下的理想行为,但我想最终得到a == 124b == 67.我目前的解决方法是将数据流式传输到ints,然后将它们复制到uint8_ts.

uint8_t a, b;
int a_, b_;
stringstream data("124 67");
data >> a_ >> b_;
a = a_;
b = b_;
Run Code Online (Sandbox Code Playgroud)

显然,这非常麻烦(而且效率稍低).是否有更简洁的方法uint8_t使用streams 读取数字(而不是字符)数据?

c++ iostream

6
推荐指数
1
解决办法
1207
查看次数

测试Visual Studio 2012控制台应用程序的输入/输出

我正在研究一个程序,它从标准输入读取一些输入,处理它,并将一些输出写入标准输出.因此,我不必每次都输入样本/测试输入,我已将输入保存到TXT文件,并将相应的预期输出保存到另一个TXT文件.

如何运行我的可执行文件(最好是在Debug或Release模式下,或者可能在profiler下),以便VS自动输入输入TXT文件?VS能否自动检查程序的输出与预期的输出TXT文件?如果它们不同的话,它会向我展示一个并排的差异会很棒.我可以设置测试框架以使用不同的输入/预期输出文件运行各种测试吗?

请注意,我不能只使用正常的单元测试,因为我必须进行集成测试.

编辑:为了它的价值,我正在使用C++.

c++ testing visual-studio-2012

5
推荐指数
1
解决办法
1592
查看次数