Объяснение вывода аргумента функции шаблона C++ при сопоставлении `T const &&t` с `int const *`

Я не понимаю, как в этом случае работает правило вывода аргументов. У меня есть следующий простой фрагмент кода:

template<typename T>
void fn(T const &&t) {
   std::cout << __PRETTY_FUNCTION__  << std::endl;
   std::cout << typeid(decltype(t)).name() << std::endl;
}
int main() {
   int const *ar = nullptr;
   std::cout << typeid(ar).name() << std::endl;
   fn(std::move(ar));
}

Результат, который я получаю, выглядит следующим образом:

PKi
void fn(const T &&) [T = const int *]
PKi

Чего я не понимаю, так это почему T выводится как const int *. Почему const не совпало с шаблоном?

какой const не совпал?

463035818_is_not_a_number 21.03.2022 10:07

const в параметре шаблона const T&& и в const int *. Я ожидал, что T станет int *, а не const int *.

Amir 21.03.2022 10:09

void fn(T const* &&t) дает то, что вы ожидали?

463035818_is_not_a_number 21.03.2022 10:11

Но const int* != int* const.

Evg 21.03.2022 10:12

Я думаю, что они @Evg

Amir 21.03.2022 10:16

Нет, это разные виды.

Evg 21.03.2022 10:16

возможно, вы имеете в виду, что int const * и int * const — это разные типы.

Amir 21.03.2022 10:20

@Amir int const * и const int * одинаковы, const int * и int * const разные, размещение const до или после * имеет значение.

songyuanyao 21.03.2022 10:22

Короткий доклад, который может показаться вам интересным: youtube.com/watch?v=fv--IKZFVO8

Bob__ 21.03.2022 10:30
Стоит ли изучать PHP в 2023-2024 годах?
Стоит ли изучать PHP в 2023-2024 годах?
Привет всем, сегодня я хочу высказать свои соображения по поводу вопроса, который я уже много раз получал в своем сообществе: "Стоит ли изучать PHP в...
Поведение ключевого слова "this" в стрелочной функции в сравнении с нормальной функцией
Поведение ключевого слова "this" в стрелочной функции в сравнении с нормальной функцией
В JavaScript одним из самых запутанных понятий является поведение ключевого слова "this" в стрелочной и обычной функциях.
Приемы CSS-макетирования - floats и Flexbox
Приемы CSS-макетирования - floats и Flexbox
Здравствуйте, друзья-студенты! Готовы совершенствовать свои навыки веб-дизайна? Сегодня в нашем путешествии мы рассмотрим приемы CSS-верстки - в...
Тестирование функциональных ngrx-эффектов в Angular 16 с помощью Jest
В системе управления состояниями ngrx, совместимой с Angular 16, появились функциональные эффекты. Это здорово и делает код определенно легче для...
Концепция локализации и ее применение в приложениях React ⚡️
Концепция локализации и ее применение в приложениях React ⚡️
Локализация - это процесс адаптации приложения к различным языкам и культурным требованиям. Это позволяет пользователям получить опыт, соответствующий...
Пользовательский скаляр GraphQL
Пользовательский скаляр GraphQL
Листовые узлы системы типов GraphQL называются скалярами. Достигнув скалярного типа, невозможно спуститься дальше по иерархии типов. Скалярный тип...
2
9
69
1
Перейти к ответу Данный вопрос помечен как решенный

Ответы 1

Ответ принят как подходящий

В объявлении параметра T const &&t, const квалифицируется на T, т. е. t объявляется как rvalue-ссылка на const T.

Когда передается ar с типом const int *, T выводится как const int *, тогда тип t будет const int * const &&, то есть rvalue-ссылка на const указатель на const int. Обратите внимание, что const квалифицируются по разным вещам (на разных уровнях), один для указателя, другой для указателя.

Спасибо за ответ. Почему T выводится как const int *. Наверное я не так понимаю typeid. Фрагмент показывает, что тип t такой же, как и тип ar, и нет дополнительной константы.

Amir 21.03.2022 10:14

@Amir Да, для typeid, Если type является ссылочным типом, результат ссылается на объект std::type_info, представляющий ссылочный тип.Во всех случаях квалификаторы cv верхнего уровня игнорируются идентификатором типа.

songyuanyao 21.03.2022 10:19

@Amir В результате typeid(const int*) == typeid(const int * const &&) это true.

songyuanyao 21.03.2022 10:19

Другие вопросы по теме