小编chu*_*ill的帖子

参数包扩展中的求值顺序问题

我写了一个模板,它接受一个istream&和一个函数,应该从 中提取这个函数的所有参数,istream用这些参数调用函数并返回结果。一切正常,除了函数参数的评估顺序。请参阅下面的代码、更多详细信息和最终问题:

#include <iostream>
#include <vector>

void Foo(int i, std::string s)
{
    std::cout << "input was " << i << " and " << s << '\n';
}

template<typename T>
T Parse(std::istream &s)
{
    T res;
    
    s >> res;
    
    return res;
}

template<typename TR, typename ... TArgs>
TR Bar(std::istream &s, TR f(TArgs...) )
{
    return f(Parse<TArgs>(s)...);
}

int main()
{
    Bar(std::cin, Foo);
}
Run Code Online (Sandbox Code Playgroud)

输入:

1 2
Run Code Online (Sandbox Code Playgroud)

预期输出:

input was 1 and 2
Run Code Online (Sandbox Code Playgroud)

实际输出:

input was 2 …
Run Code Online (Sandbox Code Playgroud)

c++ pack-expansion parameter-pack

21
推荐指数
1
解决办法
504
查看次数

在C ++ 17中实现迭代器和const_iterator的正确方法是什么?

在实现自定义容器时,我到了需要实现迭代器的地步。当然,我不想为const和non-const迭代器编写两次代码。我发现了这个问题,详细说明了这样的可能实现:

template<class T>
class ContainerIterator {
    using pointer = T*;
    using reference = T&;
    ...
};

template<class T>
class Container {
    using iterator_type = ContainerIterator<T>;
    using const_iterator_type = ContainerIterator<const T>;
}

Run Code Online (Sandbox Code Playgroud)

但是,我也发现了这个这个问题,使用模板参数:

template<class T, bool IsConst>
class ContainerIterator {
    using pointer = std::conditional_t<IsConst, const T*, T*>;
    using reference = std::conditional_t<IsConst, const T&, T&>;
    ...
};

template<class T>
class Container {
    using iterator_type = ContainerIterator<T, false>;
    using const_iterator_type = ContainerIterator<T, true>;
}
Run Code Online (Sandbox Code Playgroud)

第一个解决方案似乎更容易,但是答案是从2010年开始。经过一些研究,似乎第一个版本并未得到广泛使用,但我不知道为什么。我觉得我缺少第一个版本的一些明显缺陷。


因此问题变为:

  1. 第一个版本有什么问题吗?

  2. 如果没有,为什么版本#2似乎是c ++ …

c++ c++17

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

为什么在这个基准测试中 while(i--) 循环比 for 循环慢?

想象一个非常简单的任务,它需要一个紧密的循环,比如对数组的值求和。我编写了 5 种不同的代码来实现这一点:

const arr = Array(1000000).fill(0).map(() => Math.random());

// 1: (ab)using .forEach
let x1 = 0;
arr.forEach((i) => x1 += i);

// 2. using reduce
let x2 = arr.reduce((a, n) => a + n, 0);

// 3: classic forward for-loop
let x3 = 0;
for(let i = 0; i < arr.length; i++)
    x3 += arr[i];

// 4: backward for-loop, should be faster, because comparison with a literal is faster
let x4 = 0;
for(let i = arr.length - 1; …
Run Code Online (Sandbox Code Playgroud)

javascript benchmarking

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

存储指向std :: string数据的指针是否安全?

我的问题围绕复制构造和重新分配的机制。

我有一堂课,收集字符串。将字符串添加到集合后,该字符串将被复制并存储在向量中。但是由于我还需要访问所有字符串的集合const char * const*,因此我还通过来存储指向每个字符串数据的指针.c_str()

class MyStrings {
private:
    std::vector<std::string> names;
    std::vector<const char*> cStringPointers;
public:
    const char *const *Data() const
    {
        return this->cStringPointers.data();
    }

    void Add(const std::string &name)
    {
        // copy [name] and store the copy in [this->names].
        this->names.push_back(name); 
        // Store the pointer to the data of the copy.
        this->cStringPointers.push_back(this->names.back().c_str());
    }
}
Run Code Online (Sandbox Code Playgroud)

我知道,存储指向向量元素的指针是不好的,因为当向量被调整大小(即必须重新分配其内存)时,这些指针将不再有效。

但是我只存储指向数据的指针。所以这是我的想法:

如果names调整大小,它将移动构造它包含的所有字符串,因此这些字符串将不会分配新的内存,而是仅使用已分配的内存,因此我的指针cStringPointers仍然有效。

我的问题现在很简单:我是否错过了一些会使该代码不安全或导致未定义行为的东西?

(假设我不使用任何奇异的architexture和/或编译器。)

c++

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

EXT_scalar_block_layout 中的布局说明符标量有什么用?

scalar访问 GL_EXT_scalar_block_layout 中的存储缓冲区时,布局说明符有什么用?(例如见下文)

什么是用例scalar

背景

我最近使用 Vulkan 和 NVidias VkRayTracing 扩展程序编写了一个简单的 Raytracer,并且正在学习本教程。在有关最近命中着色器的部分中,需要访问存储在井存储缓冲区(带有使用标志vk::BufferUsageFlagBits::eStorageBuffer)中的一些数据。

在着色器中,GL_EXT_scalar_block_layout使用了扩展,并像这样访问这些缓冲区:

layout(binding = 4, set = 1, scalar) buffer Vertices { Vertex v[]; } vertices[];
Run Code Online (Sandbox Code Playgroud)

当我第一次使用这段代码时,验证层告诉我结构体Vertex的布局无效,所以我将它们更改为每个成员在 16 字节块上对齐:

struct Vertex {
    vec4 position;
    vec4 normal;
    vec4 texCoord;
};
Run Code Online (Sandbox Code Playgroud)

使用 C++ 中的相应结构:

#pragma pack(push, 1)
struct Vertex {
    glm::vec4 position_1unused;
    glm::vec4 normal_1unused;
    glm::vec4 texCoord_2unused;
};
#pragma pack(pop)
Run Code Online (Sandbox Code Playgroud)

错误消失了,我得到了一个可以工作的 Raytracer。但我仍然不明白为什么scalar这里使用关键字。我发现这个文档在谈论 GL_EXT_scalar_block_layout-extension,但我真的不明白。可能我只是不习惯 glsl 术语?我看不出我必须使用它的任何理由。

此外,我只是试图删除它 …

c++ glsl vulkan

3
推荐指数
1
解决办法
537
查看次数

是否有一些类似于扩展元素的合并元组的语法?

从 C#12 开始,该语言支持Collection 表达式,它允许使用扩展元素合并集合。

我的问题是,元组是否有一些类似的语法,特别是组合元组?(见下面的例子)

using System;

// Collection expression
int[] arr1 = [1, 2];
int[] arr2 = [3, 4];
int[] arr3 = [..arr1, ..arr2]; // combine using spread element => [1, 2, 3, 4]

// tuples, similar syntax
var tpl1 = (1, 2); 
var tpl2 = (3, 4);

// Sadly this doesn't work? 
var tpl3 = (..tpl1, ..tpl2); // Cannot implicitly convert type '(int, int)' to 'System.Index'
Run Code Online (Sandbox Code Playgroud)

我知道,我可以这样做:

var tpl3b = (tpl1.Item1, tpl1.Item2, tpl2.Item1, tpl2.Item2); …
Run Code Online (Sandbox Code Playgroud)

c#

2
推荐指数
1
解决办法
93
查看次数

Winforms ToolStrip.BackColor 返回错误的颜色

我的问题的根源

我使用 winforms 在 C# 中创建了一个非常简单的虚拟应用程序。它仅包含一个 ToolStrip 和该 ToolStrip 内的一个 TrackBar。TrackBar 应具有与 ToolStrip 相同的 BackColor,但 ToolStrip.BackColor 属性似乎不返回实际的背景颜色。

public Form1()
{
    //// Here the ToolStrip is created.
    //// This code is generated by the designer.
    this.InitializeComponent();
    //// Here the the TrackBar is created.
    //// I think this is impossible to do via the Designer.
    this.CreateSpeedSlider();
}

private void CreateSpeedSlider()
{
    this.toolStrip.SuspendLayout();
    this.speedSlider = new TrackBar
    {
        TickStyle = TickStyle.None,
        AutoSize = false,
        Height = this.toolStrip.Height,
        Minimum = 0,
        Maximum = 10, …
Run Code Online (Sandbox Code Playgroud)

c# colors toolstrip winforms

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

非常简单的程序,但为什么在 c++ 和 python 中会有如此大的不同?

我认为这两个程序功能几乎相同,但是python程序运行时间超过70秒,但是c++运行速度非常快。我不明白有什么区别?

测试1.py

import time
x = [(i%10) for i in range(10000)]
y = [(i%10) for i in range(10000)]
start = time.time()
for i in range(10000):
    if(i % 100 == 0): print("Current on %d"%i)
    for j in range(10000):
            r2 = (x[i]-x[j])**2 + (y[i]-y[j])**2

print(time.time()-start)
Run Code Online (Sandbox Code Playgroud)

测试2.cpp

#include <iostream>
#include <time.h>

int main(){
    float x[10000];
    float y[10000];
    time_t start, end;

    for(int i=0;i<10000;i++){
            x[i] = i%10;
            y[i] = i%10;
    }
    start = time(NULL);

    for(int i=0;i<10000;i++){
            if(i % 100 == 0) std::cout<<"Current on"<<i<<"\n";
            for(int j=0;j<10000;j++){ …
Run Code Online (Sandbox Code Playgroud)

c++ python

0
推荐指数
1
解决办法
128
查看次数

在 system() 函数 c++ 中使用 int 变量

我需要在我的 C++ 程序中使用 system() 函数中的 int veriable 。例如:

  • 整数a = 0;
  • 系统(“回显”a“”);

但我收到错误,我需要有关如何使用此错误的帮助:未找到 C++ 用户定义的文字运算符

c++

-1
推荐指数
1
解决办法
162
查看次数