2016-10-17 6 views
0

Позвольте p быть общим/уникальным указателем. Есть if (p) и if (p.get()) эквивалент?Умный указатель как условие: есть ли (p) и if (p.get()) равносильно?

Если нет, то в каких случаях эти условные обозначения или код в условных выражениях ведут себя по-другому?

От cppreference Я читал, что std::shared_ptr::operator bool проверяет, get() != nullptr. Является ли это точной реализацией operator bool?

+3

Вы не верите в cppreference? – NathanOliver

+0

@NathanOliver я вообще сделал! Просто хотел убедиться в этом, потому что мои общие указатели используются в многопоточной среде. – sam

+0

Почему многопоточная среда делает это по-другому? – Slava

ответ

6

«точная реализация» не должен быть ваша проблема (она будет варьироваться в зависимости от компилятора компилятора, от версии к версии, и, возможно, на основе параметров, которые вы предоставляете компилятор)

Вашего беспокойство должно быть «Как будут в соответствии со стандартами компилятор ведет себя «и ответ» Да, if(ptr) всегда должны производить те же результаты, как if(ptr.get())

от стандарта:

prvalue арифметики, незаданное перечисление, указатель , или указатель на тип члена может быть преобразован в prvalue типа bool. Значение нуля, значение нулевого указателя или значение указателя нулевого элемента преобразуется в значение false; любое другое значение преобразуется в значение true. Значение типа std :: nullptr_t может быть преобразовано в prvalue типа bool; результирующее значение ложно.

И умные указатели считаются nullable pointers, которые имеют следующее требование:

Объект р типа Р может быть преобразован в контекстуально BOOL (пункт [ко]). Эффект должен быть таким, как если бы p! = Nullptr был оценен вместо p.

(благодаря ТС для этой цитаты)

+0

Технически, этой цитаты недостаточно, так как 'unique_ptr' поддерживает причудливые указатели, а его' указатель' не обязательно является встроенным указателем. Однако это покрывается требованиями «NullablePointer». –

+0

Согласен, но я не смог найти краткую цитату, которая охватывала возможности «умных указателей». Тем не менее, насколько я знаю, все стандартные и улучшенные интеллектуальные указатели ведут себя так, как вы их ожидаете, - то, что я пытался сделать [тратить ваши усилия на беспокойство о других вещах и доверять компилятору, чтобы понять это правильно [если только вы многопоточность (которая была добавлена ​​к комментариям позже), и в этом случае не ожидайте, что компилятор прочитает ваш разум]] –

+0

[\ [unique.ptr.single \]/3] (https: //timsong-cpp.github.io/cppwp/unique.ptr.single # 3) в сочетании с [\ [nullablepointer.requirements \]/3] (https://timsong-cpp.github.io/cppwp/nullablepointer.requirements#3). –

1

Цель позади operator bool() на смарт-указатели, чтобы сделать умные указатели ведут себя как обычные указатели в общей ситуации проведения проверки действительности, то есть в ситуациях, когда вы пишете

if (myPointer) { 
    ... // Do something 
} 

Точная реализация может отличаться. Вместо того, чтобы звонить get() и сравнивать результат с nullptr, стандартная реализация может, например, проверять переменную-член, которая хранит значение, возвращаемое get(), или проверить закрытый флаг, указывающий, что указатель не указывает на что-либо действительное.

Для целей программистов, однако, достаточно знать, что реализация будет возвращать true в любое время, когда get() возвращает ненулевое значение, и что он будет также возвращать false когда get() возвращается nullptr.

1

if (p) и если (p.get()) эквивалент?

От this reference (То же самое относится к unique_ptr):

проверяет, является ли *this магазинах ненулевой указатель, то есть будь get() != nullptr.

Да, if (p) и if (p.get()) имеют эквивалентное поведение. Нет, педантично говоря, они не совсем эквивалентны: первый имеет вызов функции, последний имеет другой вызов функции и сравнение указателей. На практике оба могут генерировать идентичный код.

Если нет, то в каких случаях эти условные обозначения или код в условных выражениях ведут себя по-другому?

Они ведут себя точно так же.

Является ли это точной реализацией оператора bool?

Именно так должно осуществляться поведение.

Точная реализация - реализация определена. Вы можете прочитать источники своей стандартной реализации библиотеки, чтобы узнать.

1

Они ведут себя точно так же.

Для того, чтобы выяснить различные способы, в которых мы могли бы использовать указатель NULL проверки вы можете увидеть следующее

http://www.artima.com/cppsource/safebool.html

который называется безопасным BOOL идиома. Несмотря на то, что в C++ 11 может показаться, что он является obselete, он дает хороший exposer для использования операций bool в sharedPtrs.