libro improvements descargar book c++ c++17

improvements - c++18



¿Cómo puedo descartar intencionalmente un valor devuelto de[[nodiscard]]? (3)

La propuesta de nodcardía del WG14 discute las razones para permitir que el diagnóstico sea silenciado al vaciarlo. Dice que lanzar para anular es la forma recomendada (si no es normativa) de silenciarla, lo que sigue lo que hace la implementación existente con __attribute__((warn_unused_result)) :

El atributo [[nodiscard]] tiene un extenso uso en el mundo real, siendo implementado por Clang y GCC como __attribute __ ((warn_unused_result)), pero fue estandarizado bajo el nombre [[nodiscard]] por WG21. Esta propuesta eligió el identificador nodiscard porque la desviación de este nombre crearía una incompatibilidad innecesaria con C ++.

La semántica de este atributo se basa en gran medida en la noción de uso, cuya definición queda a discreción de la implementación. Sin embargo, la guía no normativa especificada por WG21 es alentar a las implementaciones a emitir un diagnóstico de advertencia cuando se utiliza una llamada de función nodiscard en una expresión de valor descartado potencialmente evaluada, a menos que sea una conversión explícita para anular . Esto significa que no se recomienda que una implementación realice un análisis de flujo de datos (como lo requeriría un diagnóstico de variable local inicializado pero no utilizado). ...

La forma en C ++ sería static_cast<void> .

Vea el borrador del estándar de C ++ [[ dcl.attr.nodiscard]p2 :

[Nota: una llamada a nodiscard es una expresión de llamada a la función que llama a una función declarada anteriormente nodiscard, o cuyo tipo de retorno es una clase calificada como CV o un tipo de enumeración marcado como nodiscard. Se desaconseja la aparición de una llamada de nodiscard como una expresión de valor descartado potencialmente evaluada, a menos que se haga explícitamente nula. Las implementaciones deben emitir una advertencia en tales casos. Esto suele ser porque descartar el valor de retorno de una llamada de nodiscard tiene consecuencias sorprendentes. - nota final]

Esta es una nota, por lo que no es normativa, pero básicamente esto es lo que hacen las implementaciones existentes con __attribute__((warn_unused_result)) . Además, tenga en cuenta que un diagnóstico para nodiscard también es no normativo, por lo que un diagnóstico para violar nodiscard no está mal formado, pero sí una calidad de implementación como la supresión a través de un molde para anular.

vea el documento de Clang en nodiscard, warn_unused_result :

Clang admite la capacidad de diagnosticar cuando los resultados de una expresión de llamada de función se descartan en circunstancias sospechosas. Se genera un diagnóstico cuando una función o su tipo de retorno está marcado con [[nodiscard]] (o __attribute __ ((warn_unused_result))) y la llamada a la función aparece como una expresión de valor descartado potencialmente evaluada que no se convierte explícitamente en vacío.

Di que tengo

[[nodiscard]] int foo () { return 0; } int main () { foo (); }

entonces

error: ignoring return value of ‘int foo()’, declared with attribute nodiscard [-Werror=unused-result]

pero si

int x = foo ();

entonces

error: unused variable ‘x’ [-Werror=unused-variable]

¿Hay una forma clara de decirle al compilador "quiero descartar este valor [[nodiscard]] "?


También puede etiquetar el int devuelto con otra etiqueta:

[[nodiscard]] int foo () { return 0; } int main () { [[maybe_unused]] int i = foo (); }

Podría ser útil si tiene algún código de solo depuración que requiera el valor.


Echalo al void

[[nodiscard]] int foo () { return 0; } int main () { static_cast<void>(foo()); }

Esto básicamente le dice al compilador " Sí, sé que estoy descartando esto, sí, estoy seguro de ello " .