`const shared_ptr <T>`和`shared_ptr <const T>`之间的区别?


115

我正在为C ++中的共享指针编写访问器方法,该方法如下所示:

class Foo {
public:
    return_type getBar() const {
        return m_bar;
    }

private:
    boost::shared_ptr<Bar> m_bar;
}

因此,要支持getBar()return类型的常量性,应boost::shared_ptr防止Bar它指向的修改。我的猜测shared_ptr<const Bar>要返回该类型的类型,而const shared_ptr<Bar>这将防止指针本身重新分配以指向不同的对象,Bar但允许Bar对其指向的对象进行修改。但是,我不确定。如果知道的人可以确认这一点,或者如果我弄错了,请更正我,我将不胜感激。谢谢!


3
就是你所说的 您可以查看操作员文档*->进行确认。
syam

2
T *const和之间有什么区别T const *?相同。

3
@ H2CO3完全没有。在const通常修改什么_precedes,所以T *const是一个const指针T,并且T const*是一个指针const T。最好避免const在它之前没有使用任何东西。
James Kanze

6
@JamesKanze,这是H2CO3的观点:之间的区别T *constT const *相同的区别 const shared_ptr<T>shared_ptr<const T>
乔纳森Wakely

1
@JamesKanze哦,是的。T *const是指向非常量的const指针T,也是const shared_ptr<T>。相反,T const *是的非常量指针const T,也是shared_ptr<const T>

Answers:


176

你是对的。shared_ptr<const T> p;类似于const T * p;(或等效地T const * p;),即指向的对象为,constconst shared_ptr<T> p;类似于T* const p;则表示pconst。综上所述:

shared_ptr<T> p;             ---> T * p;                                    : nothing is const
const shared_ptr<T> p;       ---> T * const p;                              : p is const
shared_ptr<const T> p;       ---> const T * p;       <=> T const * p;       : *p is const
const shared_ptr<const T> p; ---> const T * const p; <=> T const * const p; : p and *p are const.

这同样适用于weak_ptrunique_ptr


1
您还回答了我脑海中关于常规指针的问题(const T * vs. T * const vs. T const *)。:)我之所以没有提及,是因为我不希望我对SO 的问题过于广泛,这是与我当前任务有关的问题。无论如何,我想我现在很了解。谢谢!
Dave Lillethun

9
我很高兴它有所帮助。我用来记住const T* p;', 'T const * p;和的最后一个技巧T * const p。见*在意义上的分离,什么是const什么是对的同一侧*
卡西欧·内里

5
我的经验法则是const总是指左侧的东西。如果左边什么都不是,那是右边的东西。
hochl

hochi-const T * p怎么样?相当于T const * p ;?
弗拉德

卡西欧,您可以添加,对于返回类型为const shared_ptr <T>的类型,不能在非const函数中使用,而对于const指针则不适用。
弗拉德

2

boost::shared_ptr<Bar const>防止Bar通过共享指针修改 对象。作为返回值,const in boost::shared_ptr<Bar> const表示您不能在返回的临时变量上调用非const函数;如果是真正的指针(例如Bar* const),它将被完全忽略。

在一般情况下,即使在这里,通常的规则:const修改什么它之前:在boost::shared_ptr<Bar const>Bar; 在中boost::shared_ptr<Bar> const,是实例化(表达式boost::shared_ptr<Bar>为const。


1
@gatopeich所以你可以delete
Marcin

@Marcin你可以ellaborate吗?
gatopeich

1
#Check this simple code to understand... copy-paste the below code to check on any c++11 compiler

#include <memory>
using namespace std;

class A {
    public:
        int a = 5;
};

shared_ptr<A> f1() {
    const shared_ptr<A> sA(new A);
    shared_ptr<A> sA2(new A);
    sA = sA2; // compile-error
    return sA;
}

shared_ptr<A> f2() {
    shared_ptr<const A> sA(new A);
    sA->a = 4; // compile-error
    return sA;
}

int main(int argc, char** argv) {
    f1();
    f2();
    return 0;
}

我可以建议使用std::make_shared()(C ++ 14起)。
乔尔·博登曼

0

我想基于@Cassio Neri的答案进行简单演示:

#include <memory>

int main(){
    std::shared_ptr<int> i = std::make_shared<int>(1);
    std::shared_ptr<int const> ci;

    // i = ci; // compile error
    ci = i;
    std::cout << *i << "\t" << *ci << std::endl; // both will be 1

    *i = 2;
    std::cout << *i << "\t" << *ci << std::endl; // both will be 2

    i = std::make_shared<int>(3);
    std::cout << *i << "\t" << *ci << std::endl; // only *i has changed

    // *ci = 20; // compile error
    ci = std::make_shared<int>(5);
    std::cout << *i << "\t" << *ci << std::endl; // only *ci has changed

}
By using our site, you acknowledge that you have read and understand our Cookie Policy and Privacy Policy.
Licensed under cc by-sa 3.0 with attribution required.