Inicio Noticias Fundamental C - Bit básico

Fundamental C – Bit básico

Índice del artículo fundamental de C: máscaras de bits básicas Página 1 de 2 Este extracto, de mi libro sobre la programación de C en un contexto de IoT, explica los conceptos básicos de C sobre la manipulación de bits. Es crucial trabajar tanto con C que casi se puede decir que si no está manipulando los bits, probablemente esté usando el lenguaje incorrecto …

Fundamental C: acércate al coche

Ahora disponible como libro de bolsillo y libro electrónico de Amazon. Acerca de C
Consulte empleado v Independiente
& Comportamiento indefinido Introducción a C Uso de estructuras de control y variables de datos de NetBeans
Extraer variables aritméticas y representación.
Extraer expresiones y operadores aritméticos y de representación
Extraer efectos secundarios, puntos de secuencia y evaluación perezosa
Primer borrador de este capítulo: alcance de las funciones de datos de nivel inferior y matrices de por vida
Extraer matrices simples
Extraer cadenas de enumeración
Extraer punteros de cadena simples
Extraer punteros iniciales
Extraer punteros, moldear y escribir estructuras de punzón
Extraer estructuras básicas
Extraer Typedef
Manipulación de bits
Extraer bits básicos *** NUEVO
Extraer giros y rotar
Archivo
Extraer archivos Compilación C: preprocesador, compilador, enlazador
Extraer compilación y preprocesador
Consulte también el volumen complementario: Aplicación de C
La manipulación de bits está casi muerta en los lenguajes de alto nivel y no es tan común en C como antes. Sin embargo, si está escribiendo programas de bajo nivel que interactúan con el hardware de alguna manera, la manipulación de bits seguirá siendo una parte esencial de lo que hace y, para hacer las cosas bien y asegurarse de hacer las cosas de manera razonable. para dominar la técnica. La buena noticia es que no es difícil una vez que empiezas a pensar en el contenido de la memoria como un patrón de bits que tiene muchas interpretaciones.

Los operadores bit a bit

C tiene varios operadores diseñados para permitirle realizar manipulación de bits. Hay cuatro operadores bit a bit: AND & OR | XOR (exclusivo o) ^ NOT ~ Como era de esperar, el operador NOT tiene la máxima prioridad. Tenga en cuenta que también hay operadores booleanos correspondientes &&, || es ! que solo funcionan con valores booleanos, con cero como falso y cualquier cosa que no sea cero como verdadero, y no con patrones de bits. Los operadores bit a bit funcionan con tipos enteros. Por ejemplo: int a = 0xF0; int b = 0xFF; int c = ~ a & b; printf (“% X n”, c) Esto primero resuelve el NOT bit a bit de a, es decir, 0F. Esto es entonces AND bit a bit con b, es decir, 0F y FF que es F. El especificador de formato% X imprime el valor en hexadecimal. Puede utilizar% x para minúsculas y% d para decimal.

Firmado vs Sin firmar

Llegamos ahora a un punto sutil y problemático. Los operadores bit a bit se definen de forma única para valores sin signo únicamente. La razón es que los valores sin signo tienen una representación única en binario y, por lo tanto, las operaciones están bien definidas en términos de los valores representados por los patrones de bits. Es decir: valor int sin signo = 5; es siempre 0101 y por lo tanto: valor | 0x2 no solo es siempre 0111, sino que también siempre representa +7. No ocurre lo mismo con los valores con signo simplemente porque la forma en que se representan los números negativos no es fija. La representación más común es el complemento a dos, pero esto no es parte del estándar y, por lo tanto, las operaciones lógicas en números sin signo dependen de la implementación. Tenga en cuenta que esto no significa que las operaciones lógicas en valores firmados sean un comportamiento indefinido; si este fuera el caso, la mayoría de los programas en C dejarían de funcionar correctamente. Además, “dependiente de la implementación” tiene un significado bastante consistente: tome el patrón de bits que representa el valor y realice la operación lógica especificada como si todo lo involucrado fuera un valor sin signo. Esta es la única forma sensata de abordar el problema y es exactamente lo que cabría esperar. Por lo tanto, cuando el patrón de bits no está definido, como en: valor int con signo = -5; si su máquina usa la representación en complemento a dos, consulte el Capítulo 5, la secuencia de bits es: 111111111111111111111111111011 y valor | 0x4 cambia el tercer bit a 1, es decir, -1 en complemento a dos. Siempre que se asuma una representación para el valor con signo, la operación lógica generalmente está bien definida como la aplicación bit a bit del operador en patrones de bit. Es la representación la que depende de la implementación y no de la operación.

Mascaras

Entonces, ¿para qué usas los operadores lógicos bit a bit? En muchos casos existe el problema de establecer o borrar bits particulares en un valor. El valor generalmente se almacena en una variable que generalmente se trata como una variable de estado o una bandera. Puede configurar y desarmar los bits en una bandera utilizando otro valor, generalmente llamado máscara, que define los bits que se van a cambiar. Por ejemplo, si desea cambiar solo el primer bit (el menos significativo), la máscara será 0x01. Si desea cambiar el primer y segundo bits, la máscara sería 0x03 y así sucesivamente. Si le resulta difícil calcular el valor hexadecimal correcto necesario para una máscara en particular, puede usar la función strtol con una raíz de dos. Por ejemplo: char * prt; int a = strtol (“01”, & prt, 2); establecer aa 0x01 y: int a = strtol (“11”, & prt, 2); establecer en 0x03 y así sucesivamente. Para crear una máscara, simplemente anote una cadena de ceros y unos con unos en las posiciones que desea cambiar y use strtol para convertir a un valor de máscara. Ahora que tienes una máscara, ¿qué haces con ella? Suponga que la máscara de variable contiene un valor que en binario tiene uno en cada posición de bit que desea cambiar. Entonces: bandera | máscara; devuelve un patrón de bits con los mismos bits establecidos que en la máscara. Tenga en cuenta que los bits que la máscara no especifica, es decir, que son cero en la máscara, se dejan en sus valores originales. Por ejemplo: char * prt; int máscara = strtol (“11”, & prt, 2); bandera int = 0xFFF0; int resultado = bandera | máscara; printf (“% X n”, resultado); establece el resultado en 0xFFF3, es decir, establece los dos primeros bits (menos significativos). Si usa: flag & ~ mask; entonces los bits especificados en la máscara se ponen a cero o no se establecen si lo prefiere. Tenga en cuenta que se debe aplicar un operador NOT al formulario. Por ejemplo: char * prt; int máscara = strtol (“11”, & prt, 2); bandera int = 0xFFFF; int resultado = bandera & ~ máscara; printf (“% X n”, resultado); establece el resultado en 0xFFFC, es decir, desactiva los dos primeros bits. Además de configurar y deshabilitar bits particulares, es posible que también desee “voltear” los bits especificados, es decir, negarlos para que, si el bit fuera uno, se cambie a cero y viceversa. Puede hacer esto usando el operador exclusivo o (XOR): flag ^ mask invierte los bits especificados por la máscara. Por ejemplo: char * prt; int máscara = strtol (“11”, & prt, 2); bandera int = 0xFFFF; resultado int = bandera ^ máscara; printf (“% X n”, resultado); establece el resultado en 0xFFFC porque cambia los dos bits inferiores de uno a cero. También en este caso los bits no especificados por la máscara permanecen sin cambios.

Marc Gomez
Vine a por tabaco y ya me quedé aquí. Cuando no estoy en el sótano de Tecnopasion suelo pasear por las calles de Barcelona.
RELATED ARTICLES

Dejar respuesta

Please enter your comment!
Please enter your name here