BI正在enable_shared_from_this我的代码中使用,我不确定它的用法是否正确.这是代码:
class A: public std::enable_shared_from_this<A>
{
public:
void foo1()
{
auto ptr = shared_from_this();
}
};
class B:public std::enable_shared_from_this<B>
{
public:
void foo2()
{
auto ptr = shared_from_this();
}
};
class C:public std::enable_shared_from_this<C>
{
public:
void foo3()
{
auto ptr = shared_from_this();
}
};
class D: public A, public B, public C
{
public:
void foo()
{
auto ptr = A::shared_from_this();
}
};
Run Code Online (Sandbox Code Playgroud)
这些用法是否make_shared_from_this()正确,假设它们总是被shared_ptrD 调用?
c++ multiple-inheritance shared-ptr c++11 enable-shared-from-this
在与我的一位同事交谈时,他们说:
Run Code Online (Sandbox Code Playgroud)foo() { int *p; { int x = 5; p = &x; } int y = *p; }创建未定义的行为,因为生命周期规则和范围规则未指定.
然而:
Run Code Online (Sandbox Code Playgroud)foo() { int *p; { static int x = 5; p = &x; } int y = *p; }没有定义!您最终会遇到"间接范围"问题.
术语的使用听起来不正确.
我知道静态与范围无关.
第二种情况是否定义了行为?
我有使用的成员函数(方法)
std::enable_shared_from_this::weak_from_this()
Run Code Online (Sandbox Code Playgroud)
简而言之:weak_from_this返回weak_ptr到这个。一个警告是它不能从构造函数中使用。如果有人使用继承的类的构造函数中的函数,则该函数weak_from_this将返回expired weak_ptr。我通过断言检查它是否未到期来进行防范,但这是运行时检查。
有没有一种方法可以在编译时进行检查?
我读了很多人写的"一个虚拟表存在于一个已经在其中声明了虚函数的类".
我的问题是,vtable是仅存在于具有虚函数的类还是存在于从该类派生的类中.
例如
class Base{
public:
virtual void print(){cout<<"Base Print\n";}
};
class Derived:public Base{
public:
void print(){cout<<"Derived print\n";}
};
//From main.cpp
Base* b = new Derived;
b->print();
Run Code Online (Sandbox Code Playgroud)
问题:如果没有派生类的vtable,那么输出就不会是"派生打印".所以IMO存在一个vtable,用于任何已声明虚函数的类,也存在于从该类继承的类中.它是否正确 ?
在下面的代码中,似乎类C无法访问A的构造函数,这是因为虚拟继承所必需的.然而,代码仍然编译和运行.它为什么有效?
class A {};
class B: private virtual A {};
class C: public B {};
int main() {
C c;
return 0;
}
Run Code Online (Sandbox Code Playgroud)
此外,如果我从A中删除默认构造函数,例如
class A {
public:
A(int) {}
};
class B: private virtual A {
public:
B() : A(3) {}
};
Run Code Online (Sandbox Code Playgroud)
然后
class C: public B {};
Run Code Online (Sandbox Code Playgroud)
会(意外地)编译,但是
class C: public B {
public:
C() {}
};
Run Code Online (Sandbox Code Playgroud)
不会像预期的那样编译.
使用"g ++(GCC)3.4.4(cygming special,gdc 0.12,使用dmd 0.125)编译的代码",但已经验证它与其他编译器的行为相同.
c++ inheritance encapsulation virtual-inheritance private-inheritance
void在C++类型系统中是一个奇怪的疣.这是一个不完整的类型,无法完成,它有各种有关限制方式的魔术规则:
类型cv
void是不完整的类型,无法完成; 这种类型有一组空值.它用作不返回值的函数的返回类型.任何表达式都可以显式转换为cvvoid([expr.cast]).类型的表达式CVvoid应仅作为一个表达式语句,作为逗号表达式的操作数,作为一个第二或第三操作数?:([expr.cond]),作为操作数typeid,noexcept或decltype,如在表达return具有返回类型cv 的函数的语句void,或作为显式转换为cv 类型的操作数的语句void.
(N4778,[basic.fundamental]9)
除了对所有这些奇怪规则的痒感之外,由于它的使用方式有限,在编写模板时经常会出现一个痛苦的特殊情况; 通常情况下,我们希望它表现得更像std::monostate.
让我们想象一下,除了上面的引文,标准说的void是类似的东西
这是一个定义相当于以下类型的类型:
Run Code Online (Sandbox Code Playgroud)struct void { void()=default; template<typename T> explicit void(T &&) {}; // to allow cast to void };
保持void *魔法 - 可以别名任何对象,数据指针必须在往返过程中存活void *.
这个:
void"适当"类型的现有用例;return …c++ language-design generic-programming void language-lawyer
这特别是关于C++ 11:
#include <iostream>
struct A {
A(){}
int i;
};
struct B : public A {
int j;
};
int main() {
B b = {};
std::cout << b.i << b.j << std::endl;
}
Run Code Online (Sandbox Code Playgroud)
用g ++ 8.2.1编译:
$ g++ -std=c++11 -pedantic-errors -Wuninitialized -O2 a.cpp
a.cpp: In function ‘int main()’:
a.cpp:25:25: warning: ‘b.B::<anonymous>.A::i’ is used uninitialized in this function [-Wuninitialized]
std::cout << b.i << " " << b.j << std::endl
Run Code Online (Sandbox Code Playgroud)
gcc检测b.i为未初始化,但我认为它应该与零一起进行零初始化b.j.
我相信正在发生的事情(特别是C++ 11,来自ISO/IEC工作草案N3337,强调我的):
B …c++ initialization language-lawyer c++11 list-initialization
因此,显然C ++ 20正在得到std::to_address。
从cppreference页面上,它的用例对我来说似乎并不明确。我们已经有了operator&和std::addressof,为什么还需要另一个函数来为其参数提供地址?
在C ++ 20中,不赞成使用POD的概念,因为它是琐碎且标准的布局的无意义的合成特征。但是,C ++ 20草案中的POD定义并不完全是“琐碎的和标准布局”;实际上是:
POD类是既是普通类又是标准布局类的类,并且不具有非POD类类型的非静态数据成员(或其数组)。POD类型是标量类型,POD类,这种类型的数组或这些类型之一的cv限定版本。
换句话说,POD类型不仅是琐碎的而且是标准布局的,而且也是递归的。
该递归需求是否多余?换句话说,如果一个类型既是琐碎的又是标准布局,那么它是否也自动递归地变得琐碎又是标准布局?如果答案为“否”,那么标准布局,琐碎类型却不能成为POD的例子是什么?
说我有一个shared_ptr带有自定义分配器和自定义删除器的。
我在标准中找不到任何内容讨论删除器的存储位置:它没有说自定义分配器将用于删除器的内存,也没有说不会。
这是未指定的还是我只是缺少了什么?
c++ ×10
shared-ptr ×3
c++11 ×2
c++17 ×2
c++20 ×2
allocator ×1
constructor ×1
inheritance ×1
lifetime ×1
scope ×1
static ×1
void ×1
vtable ×1
weak-ptr ×1