Технически вы не бросаете реальный объект, вы бросаете его копию. Вот почему вы можете сойти с рук, бросив временный. Поймав ссылку, вы получите ссылку на копию.
Это может вас укусить, если вы выбросите исключение из блока catch, вы можете стать жертвой проблемы срезов. Вот почему вы не делаете:
catch (std::exception & e)
{
throw e; // bad, always throws std::exception rather than what was caught
}
а точнее
catch (std::exception & e)
{
throw; // good, rethrows the exact copy that you caught without making another copy
}
P.S. Нет правила, гласящего, что вы не можете вернуть строку UTF-8 из what
. Это было бы до вас, чтобы преобразовать его в UTF-16 для ввода-вывода Windows. Стандартные классы исключений никогда не были специально разработаны или расширены для Unicode, а также не добавлены какие-либо нестандартные расширения только для Windows.