小编Ber*_*ard的帖子

C++ make变量的类型取决于上下文?

我有以下代码:

// Case #1
float f = 1.0f;
float f2 = sqrt(f * pi);

// Case #2
double d = 1.0;
double d2 = sqrt(d * pi);
Run Code Online (Sandbox Code Playgroud)

有什么办法来定义变量pi,以便operator*sqrt将在操作floatS IN案例#1,但在操作double中的情况#2秒?

也许C++ 14变量模板可能有用吗?

c++ variable-templates c++14

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

C++中有可能什么都不扔?

在特殊情况下,我希望我的程序停止处理,输出错误std::cerr,清理和退出.

但是,调用exit()不会调用已构造的任何对象的所有析构函数.我想要很好地调用析构函数,所以我将所有代码包装在一个try-catch块中,如下所示:

int main(int argc, char** argv){
    try {
        bool something_is_not_right = false;
        /* lots of variables declared here */
        /* some code that might set something_is_not_right to true goes here */
        if(something_is_not_right){
            std::cerr << "something is not right!!!" << std::endl;
            throw '\0';  // dummy unused variable for throwing.
        }
    }
    catch (...) {}
    return 0;
}
Run Code Online (Sandbox Code Playgroud)

通过这种方式,我可以保证破坏所有变量.但我似乎无法找到让C++ throw无所作为的方法. throw;在C++中有特殊意义; 它什么都不扔.

有什么方法可以throw吗?

c++ destructor exception throw

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

转发模板参数的常量,我应该使用转发引用吗?

我想编写一个foo应该调用operator()其参数的函数,如下面(破碎)代码所示:

template <typename T> void foo(const T& x){
    x();
}

struct MyFunctor{
    int data;
    void operator()(){
        /* stuff that might modify the data */
    }
};

int main()
{
    foo(MyFunctor{});
}
Run Code Online (Sandbox Code Playgroud)

显然代码不起作用,因为operator()它是非的const,但foo()需要它的参数const.

作为模板函数,foo()应该使用两个const和非const函子,并且不要挑剔const它的参数的性质.

如果我foo()通过删除const以下内容进行更改:

template <typename T> void foo(T& x) { /* ... */ }
Run Code Online (Sandbox Code Playgroud)

...它也不起作用,因为你无法将右值引用转换为非const左值引用,因此foo(MyFunctor{})无法调用.

更改foo()为转发引用可解决所有问题:

template <typename T> …
Run Code Online (Sandbox Code Playgroud)

c++ templates const c++11 forwarding-reference

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

成员函数的完美转发和引用限定符

C++11 引入了引用限定成员函数以及完美转发的功能。但我们可以将它们混合在一起吗?

考虑这个(工作)示例:

struct bar{
    std::string str;
    void do_stuff() & {
        /* version 1 */
    }
    void do_stuff() && {
        /* version 2 */
    }
};

struct foo{
    bar data;
    void do_stuff() & {
        data.do_stuff();
    }
    void do_stuff() && {
        std::move(data).do_stuff();
    }
};

int main(){
    foo f;
    f.do_stuff() // calls version 1 of bar::do_stuff()
    std::move(f).do_stuff() // calls version 2 of bar::do_stuff()
}
Run Code Online (Sandbox Code Playgroud)

在内部main(),第一个调用调用版本 1 或bar::do_stuff(),第二个调用调用版本 2 或bar::do_stuff()。中存在一些重复的代码foo::do_stuff()。如果 ref-qualifiers 用于除隐含的参数之外的参数*this,我们可以轻松地进行完美转发:

template …
Run Code Online (Sandbox Code Playgroud)

c++ perfect-forwarding c++11 ref-qualifier

5
推荐指数
0
解决办法
131
查看次数

编译器通常会在没有明确告知的情况下发出向量(SIMD)指令吗?

C++ 17为标准库添加了并行扩展(例如std::sort(std::execution::par_unseq, arr, arr + 1000),允许使用多个线程和向量指令进行排序).

我注意到微软的实验性实现提到VC++编译器缺乏对这里做矢量化的支持,这让我感到惊讶 - 我认为现代C++编译器能够推断出循环的可矢量化,但显然VC++编译器/优化器无法生成SIMD代码即使明确告知这样做.看似缺乏自动矢量化支持与2011年关于Quora的问题的答案相矛盾,这表明编译器将在可能的情况下进行矢量化.

也许,编译器只会对非常明显的情况进行矢量化,例如a std::array<int, 4>,而且只不过是这样,因此C++ 17的显式并行化会很有用.

因此我的问题是:当没有明确告知这样做时,当前的编译器会自动向量化我的代码吗?(为了使这个问题更具体,让我们将其缩小到支持SIMD的Intel x86 CPU,以及最新版本的GCC,Clang,MSVC和ICC.)

作为扩展:其他语言的编译器是否可以做更好的自动矢量化(可能是由于语言设计)(因此C++标准委员会认为它对于显式(C++ 17风格)矢量化是必要的)?

parallel-processing simd vectorization auto-vectorization c++17

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

在Visual Studio 2017中使用64位Visual C ++工具集

我的(相当大的)C ++项目已经发展到C1060: compiler is out of heap space在尝试编译项目时出现错误的地步。

我正在64位Windows 10机器上进行编译,但似乎Visual Studio正在使用32位工具集来编译我的项目(请参见下面的屏幕截图)。

32位编译器驱动程序

C1060帮助页面要求我使用64位的工具集,但提供的链接了解如何只用命令行编译时启用了会谈。

是否可以在Visual Studio 2017中设置项目属性或其他方式来告诉它使用64位编译器工具集(已安装在我的计算机上)?

visual-studio visual-studio-2017

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

当 Vec 移动时,我可以(不安全地)持有指向 Vec 元素的指针吗?

我正在实现一个算法,为了保持所需的时间复杂度,我想在移动Vec时保存一个指向元素的指针。Vec

具体来说,是这样的:

fn main() {
    let mut v: Vec<usize> = vec![1, 2, 3];
    let ptr: *mut usize = &mut v[1] as *mut usize;
    let mut u: Vec<usize> = v;
    assert!(ptr == &mut u[1] as *mut usize);
    println!("{}", unsafe { *ptr });
}
Run Code Online (Sandbox Code Playgroud)

实际的代码更复杂,涉及树状数据结构,其中每个顶点拥有一个Vec子节点。我在这里不是在问编码风格,但我的问题是是否可以依赖这段代码来完成我认为它所做的事情。

由于Vec必须将其内容保存在堆上,并且移动相当于memcpyRust,我认为可移动的事实Vec意味着我的代码是健全的(即不是未定义的行为)。它是否正确?

pointers unsafe vector move-semantics rust

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

C++默认参数为另一个参数

我可以使用第一个参数作为第二个参数的默认值,像这样吗?

int do_something(int a, int b = a + 1){
    /* ... */
}
Run Code Online (Sandbox Code Playgroud)

我的编译器似乎不喜欢它,所以也许它是不允许的.

c++ parameters

4
推荐指数
2
解决办法
127
查看次数

从C++中的另一个线程读取指针

在下面的代码中,x由于原子线程围栏,线程2中的值将始终为10.

int x;
atomic<bool> b(false);

// thread 1:
x = 10;
atomic_thread_fence(memory_order_release);
b = true;

// thread 2:
while(!b){}
atomic_thread_fence(memory_order_acquire);
assert(x == 10); // x will always be 10
Run Code Online (Sandbox Code Playgroud)

但是在下面的代码中,*x线程2中的总是10?

int* x = new int;
atomic<bool> b(false);

// thread 1:
*x = 10;
atomic_thread_fence(memory_order_release);
b = true;

// thread 2:
while(!b){}
atomic_thread_fence(memory_order_acquire);
assert(*x == 10); // will *x always be 10?
Run Code Online (Sandbox Code Playgroud)

c++ multithreading pointers atomicity

4
推荐指数
1
解决办法
615
查看次数

从C++中的字符串文字返回const char*?

通常,我会std::string从函数返回a ,因为返回a const char*将要求调用者提供输出内存缓冲区,并且该缓冲区不可调整大小.

但是const char*从字符串文字返回一个有效的if?

const char* generate_c_string() {
    return "ABC";
}
Run Code Online (Sandbox Code Playgroud)

这样做(如果有效)可能会更快,因为我不需要动态分配内存来构造一个std::string.

它可能是有效的,因为它const char* x = "ABC";是有效的.是否有来自C++标准的参考资料证实其有效性?

c++ const-char string-literals c++17

4
推荐指数
1
解决办法
829
查看次数