Espacios de nombres
Variantes
Acciones

Sustitución mediante macros de texto

De cppreference.com

 
 
Lenguaje C++
Los temas generales
Original:
General topics
The text has been machine-translated via Google Translate.
You can help to correct and verify the translation. Click here for instructions.
Control de flujo
Original:
Flow control
The text has been machine-translated via Google Translate.
You can help to correct and verify the translation. Click here for instructions.
Sentencias condicionales ejecución
Original:
Conditional execution statements
The text has been machine-translated via Google Translate.
You can help to correct and verify the translation. Click here for instructions.
Instrucciones de iteración
Original:
Iteration statements
The text has been machine-translated via Google Translate.
You can help to correct and verify the translation. Click here for instructions.
Ir declaraciones
Original:
Jump statements
The text has been machine-translated via Google Translate.
You can help to correct and verify the translation. Click here for instructions.
Funciones
Original:
Functions
The text has been machine-translated via Google Translate.
You can help to correct and verify the translation. Click here for instructions.
declaración de la función
lambda declaración de la función
función de plantilla
especificador inline
especificaciones de excepción (obsoleto)
noexcept especificador (C++11)
Excepciones
Original:
Exceptions
The text has been machine-translated via Google Translate.
You can help to correct and verify the translation. Click here for instructions.
Los espacios de nombres
Original:
Namespaces
The text has been machine-translated via Google Translate.
You can help to correct and verify the translation. Click here for instructions.
Tipos
Original:
Types
The text has been machine-translated via Google Translate.
You can help to correct and verify the translation. Click here for instructions.
decltype specifier (C++11)
Los especificadores
Original:
Specifiers
The text has been machine-translated via Google Translate.
You can help to correct and verify the translation. Click here for instructions.
cv especificadores
almacenamiento duración especificadores
constexpr especificador (C++11)
auto especificador (C++11)
alignas especificador (C++11)
Inicialización
Original:
Initialization
The text has been machine-translated via Google Translate.
You can help to correct and verify the translation. Click here for instructions.
Los literales
Original:
Literals
The text has been machine-translated via Google Translate.
You can help to correct and verify the translation. Click here for instructions.
Expresiones
Original:
Expressions
The text has been machine-translated via Google Translate.
You can help to correct and verify the translation. Click here for instructions.
representaciones alternativas
Utilidades
Original:
Utilities
The text has been machine-translated via Google Translate.
You can help to correct and verify the translation. Click here for instructions.
Tipos
Original:
Types
The text has been machine-translated via Google Translate.
You can help to correct and verify the translation. Click here for instructions.
typedef declaration
alias de tipo de declaración (C++11)
atributos (C++11)
Lanza
Original:
Casts
The text has been machine-translated via Google Translate.
You can help to correct and verify the translation. Click here for instructions.
conversiones implícitas
const_cast conversion
static_cast conversion
dynamic_cast conversion
reinterpret_cast conversion
C-cast estilo y funcional
De asignación de memoria
Original:
Memory allocation
The text has been machine-translated via Google Translate.
You can help to correct and verify the translation. Click here for instructions.
Clases
Original:
Classes
The text has been machine-translated via Google Translate.
You can help to correct and verify the translation. Click here for instructions.
Clase propiedades específicas de la función
Original:
Class-specific function properties
The text has been machine-translated via Google Translate.
You can help to correct and verify the translation. Click here for instructions.
Funciones especiales miembro
Original:
Special member functions
The text has been machine-translated via Google Translate.
You can help to correct and verify the translation. Click here for instructions.
Plantillas
Original:
Templates
The text has been machine-translated via Google Translate.
You can help to correct and verify the translation. Click here for instructions.
clase de plantilla
función de plantilla
plantilla de especialización
paquetes de parámetros (C++11)
Varios
Original:
Miscellaneous
The text has been machine-translated via Google Translate.
You can help to correct and verify the translation. Click here for instructions.
Montaje en línea
 
 

El preprocesador permite la sustitución con macros de texto. También se permite macros en forma de función, con parámetros.

Contenido

[editar] Sintaxis

#define identificador contenido de sustitución (opcional) (1)
#define identificador(parámetros) contenido de sustitución (opcional) (2)
#define identificador(parámetros, ...) contenido de sustitución (opcional) (3) (desde C++11)
#define identificador(...) contenido de sustitución (opcional) (4) (desde C++11)
#undef identificador (5)

[editar] Explicación

[editar] Directiva #define

La directiva #define establece un identificador como macro, es decir, le indica al compilador que sustituya todas las apariciones sucesivas de identificador por el contenido de sustitución, que puede estar a su vez adicionalmente procesada. Si el identificador ya está definido como cualquier tipo de macro, el programa es erróneo, está mal formado, a menos que las definiciones sean idénticas.

[editar] Macros como objetos

Una macro de este tipo reemplaza todas las apariciones del identificador definido por el contenido de sustitución. La forma (1) de la directiva #define se comporta de esta manera.

[editar] Macros con forma de función

Una macro con forma de función reemplaza todas apariciones de el identificador definido por el contenido de sustitución, además de tomar una serie de argumentos, que a continuación reemplazará las ocurrencias de cualquiera de los parámteros en el contenido de sustitución. Al utilizar una macro de este tipo el número de argumentos debe ser el mismo que el número de argumentos especificado en la declaración de la macro, (parámetros), o el programa es erróneo. Si el identificador no está en forma de función, es decir, no tiene paréntesis después de sí misma, no se sustituye nada.

La forma (2) de la directiva #define es la declaración simple de una macro con forma de función. En este caso el número de argumentos debe coincidir en la declaración y en el momento de uso.

La forma (3) de la directiva #define declara una macro en forma función similar a la anteriro, pero con un número variable de argumentos. A los argumentos adicionales se puede acceder utilizando el identificador __VA_ARGS__, que luego se reemplaza por los argumentos, suministrados con el identificador de la macro.

La forma (4) de la directiva #define declara una macro de tipo función con un número variable de argumentos, pero sin argumentos normales. Los argumentos sólo son accesibles con el identificador __VA_ARGS__, que luego se reemplaza por los argumentos, suministrados con el identificador de la macro.

[editar] Operadores # y ##

En las macros de tipo función, un operador # antes de un identificador en el contenido de sustitución, procede al reemplazo de parámetros y encierra el resultado entre comillas, creando una cadena de texto. Además, el preprocesador añade barras inversas (\) para escapar las comillas, si las hay, dentro de la cadena de texto, y dobla las barras invertidas (\\) dentro de la cadena si es necesario. Se eliminan todos los espacios en blanco iniciales y finales, y cualquier secuencia de espacios en blanco dentro del texto (pero no dentro de las cadenas de texto embebidas) se convierte en un solo espacio. Esta operación se denomina "conversión a cadena". Si el resultado de la “conversión a cadena” no es una cadena de texto válida, el comportamiento es indeterminado.

Un operador ## entre dos identificadores sucesivos en el replacement-list corre el reemplazo de parámetros en los dos identificadores y luego concatena el resultado. Esta operación se denomina "concatenación" o "token pegar". Sólo tokens que forman un símbolo válido juntos se puede pegar: identificadores que forman un identificador más largo, los dígitos que forman un número u operadores + y = que forman una +=. Un comentario no puede ser creado por / pegar y * porque los comentarios se eliminan de texto antes de la sustitución de macros se considera. Si el resultado de la concatenación no es un token válido, el comportamiento no está definido .
Original:
A ## operator between any two successive identifiers in the replacement-list runs parameter replacement on the two identifiers and then concatenates the result. This operation is called "concatenation" or "token pasting". Only tokens that form a valid token together may be pasted: identifiers that form a longer identifier, digits that form a number, or operators + and = that form a +=. A comment cannot be created by pasting / and * because comments are removed from text before macro substitution is considered. If the result of concatenation is not a valid token, the behavior is undefined.
The text has been machine-translated via Google Translate.
You can help to correct and verify the translation. Click here for instructions.

[editar] Directiva #undef

La directiva #undef deshabilita el identificador, es decir, se cancela la anterior declaración de la directiva #define identificador. Si el identificador no estaba declarado como una macro, la directiva se ignora.

[editar] Macros predefinidas

Los nombres de las siguientes macros están predefinidas en cualquier compilador.

__cplusplus
indica la versión estándar de C++ en uso, tiene el valor 199711L(hasta C++11), 201103L(C++11), 201402L(C++14) o 201703L(C++17).
(macro constante)
__STDC_HOSTED__
(C++11)
tiene un valor entero contante 1 si la aplicación está alojada (se ejecuta en un sistema operativo), y 0 si es independiente (funciona sin un sistema operativo).
(macro constante)
__FILE__
se sutituye por el nombre del archivo actual, como una cadena de caracteres
(macro constante)
__LINE__
se sutituye por el número de línea en el archivo fuente, en forma de constante entera
(macro constante)
__DATE__
se sutituye por la fecha de la compilación, como uns cadena de caracteres de la forma "mmm dd aaaa". El nombre del mes es como el generado por la función std::asctime()
(macro constante)
__TIME__
se sustituye por la hora en que se realizó la compilación, como cadena de caracteres de la forma "hh: mm: ss".
(macro constante)

Los siguientes nombres de macro adicionales pueden estar predefinidas por las implementaciones .|The following additional macro names may be predefined by the implementations.

__STDC__
valor definido por la aplicación. Si está presente, normalmente se usa para indicar que se cumple con la norma de C.
(macro constante)
__STDC_VERSION__
(C++11)
valor definido por la aplicación. Si está presente indica la versión estándar de C (un entero largo constante de valor aaaammL, donde aaaa es el año y mm el mes).
(macro constante)
__STDC_ISO_10646__
(C++11)
se expande a una constante entera de la forma aaaammL, si wchar_t utiliza Unicode, la fecha indica la última revisión de Unicode compatible.
(macro constante)
__STDC_MB_MIGHT_NEQ_WC__
(C++11)
tiene valor 1 si la codificación extendida de caracteres del juego de caracteres básico no puede ser igual a su codificación de un byte.
(macro constante)
__STDCPP_STRICT_POINTER_SAFETY__
(C++11)
tiene valor 1 si la aplicación tiene valor strict para std::pointer_safety
(macro constante)
__STDCPP_THREADS__
(C++11)
de valor 1 si el programa puede tener más de un hilo de ejecución
(macro constante)

Los valores de estos macros (excepto __FILE__ y __LINE__) permanecen constantes a lo largo de la compilación. Los intentos por redeclarar o eliminar la definición de estas macros da como resultado un comportamiento indeterminado

Nota: dentro del cuerpo de cada función, hay una variable local predefinida especial, llamada __func__(desde C++11), que se define como una cadena de caracteres estática que contiene el nombre de la función en un formato definida por la aplicación. No es una macro de preprocesador, pero se usa junto con __FILE__ y __LINE__, por ejemplo, por assert.

[editar] Ejemplo

#include <iostream>
 
//hacer un creador de funciones y utilizarlo
#define FUNCION(nombre, a) int fun_##nombre() {return a;}
 
FUNCION(abcd, 12);
FUNCION(fff, 2);
FUNCION(kkk, 23);
 
#undef FUNCION
#define FUNCION 34
#define SALIDA(a) std::cout << #a << '\n'
 
int main()
{
    std::cout << "abcd: " << fun_abcd() << '\n';
    std::cout << "fff: " << fun_fff() << '\n';
    std::cout << "kkk: " << fun_kkk() << '\n';
    std::cout << FUNCION << '\n';
    SALIDA(mitexto);               //no son necesarias comillas
}

Salida:

abcd: 12
fff: 2
kkk: 23
34
mitexto