简体   繁体   中英

Not understanding C++ type mismatch: const Foo* to Foo* const&

Having this set of objects and statements:

QSet<Foo*> set;
iterator QSet::insert(const T & value)    //type of the function I want to call
const Foo * get() const                   //type of the function I use to get the argument

set.insert(get());                        //the line showing up as error

I get the error "no known conversion for argument 1 from 'const Foo*' to 'Foo* const&". I guess I have trouble reading these types because I have no idea what I should do to make this work.

From what I've read, the const keyword applies to the type to its left with the exception of a top-level const which can be written to the left of the type it applies to. My guess would be that I have to convert get() to a reference but I'm unsure how to do that.

There seem to be a couple of misunderstandings here (both by the questioner and by some answers).

First , you said "My guess would be that I have to convert get() to a reference but I'm unsure how to do that". Let's try clearing this up:

1) "I have to convert get() to a reference" -- Actually, you don't!

iterator QSet::insert(const T & value) does indeed take a reference. But it's a reference to type T . So the question is, "what is type T "?

In this case, T=Foo * . So insert , in this instance of the template, is actually:

iterator QSet::insert(Foo * const & value) -- read it from right to left: insert takes a reference to a constant pointer to a Foo .

2) "I'm unsure how to do that [convert a pointer to a reference]" -- while you don't have to do it here, in general you do this by de-referencing the result of get. For example: *(get()) .

Second , the compiler error. The error arises because there is a conflict:

a) get() returns a const Foo *

b) but set stores a Foo* -- NOT a const Foo * , so insert only accepts a changeable Foo

So you can't store a constant pointer inside your QSet<Foo*> . This makes sense because you can use set to access and change the Foo s inside it, which you promise not to do with a const Foo .

This reference should be helpful:

https://isocpp.org/wiki/faq/const-correctness

You may also think whether you can just use a QSet<Foo> instead of a QSet<Foo*> . In the former case, things will probably behave how you expect.

您正在尝试使用const Foo *并将其插入到QSet<Foo *> ,但编译器不会自动将const Foo *转换为普通Foo *以执行此操作。

I solved the problem by changing the type of the set as follows.

QSet<Foo const*> set;

With this change, compilation succeeds.

You're violating the const-ness of the pointer returned from your get() function. get() returns a pointer to a const object of type Foo , but then you try to insert it into a vector of non-const Foo pointers. You need to const_cast the return value from get() or change the return type of get() from const Foo* to just Foo* .

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM