Предположим, у меня есть вызываемый тип, например:
struct mutable_callable
{
int my_mutable = 0;
int operator()() { // Not const
return my_mutable++;
}
};
Обратите внимание, что mutable_callable
есть неконстантный, operator()
который изменяет переменную-член .....
Теперь предположим, что я создал std::function
из моего типа:
std::function<int()> foo = mutable_callable{};
Теперь я могу сделать это:
void invoke(std::function<int()> const& z)
{
z();
}
int main()
{
invoke(foo); // foo changed.....oops
}
Теперь, насколько я могу сказать , std::function
S operator()
является const
в соответствии с :
https://en.cppreference.com/w/cpp/utility/functional/function/operator ()
Так что мое внутреннее ощущение, что вы не должны быть в состоянии сделать это .....
Но потом посмотрим: https://en.cppreference.com/w/cpp/utility/functional/function/function
Кажется, это не накладывает никаких ограничений на то, имеет ли вызываемый тип константу operator()
......
Итак, мой вопрос заключается в следующем: я правильно предположил, что std::function<int()> const&
это, по сути, одно и то же, как std::function<int()>&
то, что на самом деле нет разницы между поведением двух ... и если это так, то почему это не const
правильно?
источник
std::function
имеет эквивалентstruct a{ std::any x; };
в нем .....std::function
реализации MSVC : i.stack.imgur.com/eNenN.png гдеusing _Ptrt = _Func_base<_Ret, _Types...>
. Я считаю так.Ответы:
Это сводится к тому же , как
struct A { int* x; };
, где вconst A a;
вы можете изменить значение из*(a.x)
(но не там , где он указывает). Существует уровень косвенностиstd::function
(от стирания типа), через которыйconst
не распространяется.И нет,
std::function<int()> const& f
это не бессмысленно. В astd::function<int()>& f
вы сможете назначить другой функторf
, который вы не можете сделать в этомconst
случае.источник
std::vector
делает это,std::unique_ptr
не делает. Я чувствую,std::function
что на самом деле речь не идет о выражении инвариантов состояния функтора. Может быть, мы могли бы повторно использовать отвратительные типы функций (т.е.std::function<int() const>
), чтобы различать?unique_ptr
не должен распространять константу, как это делает обычный указатель. Иstd::function<int() const>
не будет компилироваться.std::function
следует относиться, мне не ясно. И этоstd::function<int() const>
было гипотетически - конечно, он не компилируется сейчас, но будет ли он удовлетворять, например, OP здесь, если это можно сделать допустимым, выражая «можно назначать только функторы сoperator() const
(или без состояния)»? (даже если за кулисами это было бы довольно жестоко из-за использования отвратительных типов функций)?