相关疑难解决方法(0)

C++:临时论证的生命周期?

当创建a的新实例MyClass作为函数的参数时,如下所示:

class MyClass
{
  MyClass(int a);
};    

myFunction(MyClass(42));
Run Code Online (Sandbox Code Playgroud)

该标准是否使得任何被授权者都能获得析构函数的时间安排?
具体来说,我可以假设在调用之后的下一个语句之前调用它myFunction()吗?

c++ destructor

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

为什么在范围块结束之前,未命名的C++对象会被破坏?

以下代码打印一,二,三.对于所有C++编译器来说,这是否合乎需要?


class Foo
{
      const char* m_name;
public:
      Foo(const char* name) : m_name(name) {}
      ~Foo() { printf("%s\n", m_name); }
};

void main()
{
      Foo foo("three");
      Foo("one");   // un-named object
      printf("two\n");
}
Run Code Online (Sandbox Code Playgroud)

c++ destructor scope

17
推荐指数
3
解决办法
5519
查看次数

string.c_str()是const?

我在库中有一个函数,它接受char*并修改数据.

我试图给它,c_str()但c ++文档说它返回一个const char*.

除了新建一个char数组并将其复制到其中之外,我还能做些什么呢?

c++

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

是否定义了将xvalues转换为左值以传递给函数?

最近我发现 ,有时能够将rvalues 暂时变成左值对我来说很有用.

我一直在使用以下工具:

#include <type_traits>

template <typename T>
inline constexpr std::remove_reference_t<T> &lvalue(T &&r) noexcept {
    return static_cast<std::remove_reference_t<T> &>(r);
}
Run Code Online (Sandbox Code Playgroud)

当您必须使用需要左值作为参数的函数时,它很有用,但您对这些特定值的变化没有任何兴趣.当您对与给定的特定参数无关的其他输出向量感兴趣时.

例如,这个:

std::string get_my_file() {
    std::ifstream ifs("myfile.txt");
    return {std::istreambuf_iterator<char>(ifs), {}};
}
Run Code Online (Sandbox Code Playgroud)

可以改为:

std::string get_my_file() {
    return {std::istreambuf_iterator<char>(lvalue(std::ifstream("myfile.txt"))),
            {}};
}
Run Code Online (Sandbox Code Playgroud)

还有这个:

std::string temp1 = get_my_shader();
const char *temp2 = temp1.c_str();
glShaderSource(a, 1, &temp2, nullptr);
Run Code Online (Sandbox Code Playgroud)

可以改为:

glShaderSource(a, 1, &lvalue(get_my_shader().c_str()), nullptr);
Run Code Online (Sandbox Code Playgroud)

并允许这样的事情:

void foo(int *x) {
    std::cout << *x << std::endl;
}

foo(&lvalue(5));
Run Code Online (Sandbox Code Playgroud)

我想确定我是否在调用任何未定义的行为,因为我没有看到任何行为,尽管可能会有一些转换规则将其视为非法(我忽略).关于临时的生命,我没有看到问题,因为AFAIK,rvalues直到完全表达结束并且函数的使用仅限于此.

有一个最近约标准的变化reinterpret_castxvalues …

c++ undefined-behavior language-lawyer c++11 c++14

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

解除引用临时std :: shared_ptr是否安全?

解除引用临时std :: shared_ptr是否安全?

例:

std::shared_ptr<std::string> create_shared_string()
{
  return std::shared_ptr<std::string>(new std::string("hello"));
}

std::cout << *create_shared_str() << std::endl;
Run Code Online (Sandbox Code Playgroud)

我担心,一旦取消引用完成,shared_ptr就会被销毁,引用计数器会变为零,因此返回的原始指针不再安全.

c++ memory-management stl visual-c++

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

这是正确使用临时std :: string吗?

std::string getMyString() { return <make a string>; }

...

HANDLE something = OpenSomething(getMyString().c_str(), ...);
Run Code Online (Sandbox Code Playgroud)

我已经读过C++中的临时保证生命周期,并且我相信临时字符串将一直存在,直到评估了赋值,即足够长以使其按预期工作.

有一次遇到与std::string生命有关的错误(不记得是什么)我宁愿仔细检查......

c++ object-lifetime

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

运算符+序列中的临时生命周期

可能重复:
C++中临时的保证寿命?
临时的一生

当从重载operator+方法返回时,我有一个关于临时对象的生命周期的快速问题.例如,如果表达式......

a = b + c + d + e
Run Code Online (Sandbox Code Playgroud)

...是通过重载operator+方法返回临时对象来评估的,是b + c整个表达式的子表达式返回的临时范围?

由于g ++似乎保留在所有临时值上,而整个表达式都在范围内,因此可以在a =赋值期间对这些值进行延迟评估.

有人可以确认是否所有C++实现都能保证这种行为?

c++

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

C ++如何将字符作为数字而不是字符作为字符

我发现自己经常使用包含非常小的数字范围(通常从1到10)的变量,并希望通过使用char数据类型而不是int甚至是short来最小化我使用的内存量。我想将cin值转换为char变量,而无需将cin转换为ASCII等效值,也无需使用单引号。即,以下内容:

cout<< "Pick from 1 to 10.";

char selection;

cin>> selection;

if (selection == 1) return 1;
Run Code Online (Sandbox Code Playgroud)

等等...

有一种通用的方法吗?同样,我不想使用单引号。

谢谢

c++ cin char

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

从临时变量返回的引用是否有效?

我遇到过这样一种情况,即能够将方法调用链接到临时变量会非常有用:

draw(Quad(0, 0, 1, 1).rotate(90));  // <-- .rotate() returns a Quad reference

struct Quad{
    Quad(float x, float y, float width, float height){...}
    Quad & rotate(float degrees){
        ...
        return *this;
    }
}
Run Code Online (Sandbox Code Playgroud)

但是,我不确定临时变量是否会保持活动足够长时间以使draw()函数使用它.这样做安全吗?

c++ object-lifetime chaining

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

C++ 单线。在同一行上构造对象和调用函数是否合法

此代码似乎在启用优化的广泛使用的编译器上中断,尽管它在 Visual Studio 中运行良好。

struct foo
{
    foo(int a) { s[0] = '0'+a%10;s[1] = '\0'; }
    const char * bar() const { return &s[0]; }
    char s[4];
};

int main( )
{
    const char * s = foo(1234).bar();
    printf("%p %s\n", s, s);
}
Run Code Online (Sandbox Code Playgroud)

我希望即使 foo 是一个右值,它也会在堆栈上构造,并且 's' 将指向有效数据。但是,对于 GCC(版本 7.5 和 9),缓冲区永远不会被初始化。

编译失败示例:

g++-9 --std=c++11 -Wall -pedantic -O3 -o example example.cpp
Run Code Online (Sandbox Code Playgroud)

c++

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