Estructura, enumeración, puntos de conocimiento conjuntos

Estructura: una colección de elementos con el mismo o diferentes tipos.

La estructura también es un tipo.
La estructura solo se puede definir cuando se inicializa, no en forma de asignación, si quieres operar puedes ·usar operadores.
Lo mismo ocurre con las matrices, si desea asignar valores, puede usar bucles.

struct stu {
	char name[20];
	char sex[5];
	int age;
	char number[10];
};

No se permite que esté vacío en la estructura (requisito estándar C). Las palabras vacías no tienen un significado práctico.

Los miembros de la estructura pueden ser escalares, matrices, punteros y otras estructuras.

1. Acceso de miembros en la estructura:

  1. Las variables de estructura acceden a los miembros y los miembros de las variables de estructura se acceden a través de ·operadores. Como:
struct stu {
	char name[20];
	char sex[5];
	int age;
	char number[10];
};

int main()
{
	struct stu s;
	s.age = 20;
	return 0;
}
  1. El puntero de estructura accede al miembro que apunta a la variable, el puntero a la estructura.
struct stu {
	char name[20];
	char sex[5];
	int age;
	char number[10];
};

int main()
{
	struct stu s = {"小花","女",18,"192001"};
	struct stu *p = &s;
	printf("姓名:%s\n性别:%s\n年龄:%d\n学号:%s\n", p->name, p->sex, p->age, p->number);
	return 0;
}

Utilice ->operadores para acceder.
 
 
 
2. Transferencia de parámetros de estructura

Cuando se pasan los parámetros de la estructura, los parámetros deben insertarse en la pila (instanciación de parámetros formales), la estructura no tiene "degeneración, reducción de dimensionalidad" y otros problemas, y se producirá el problema de copia impresa correspondiente. Como resultado, la eficiencia es muy baja (la sobrecarga del sistema es grande y el rendimiento se reduce). Generalmente, se recomienda utilizar punteros de estructura.

Incluso si hay matrices en la estructura, no se producirá una reducción de la dimensionalidad y todas son copias impresas.

 
Si el tipo de estructura es el mismo depende de si es la misma variable de estructura. Incluso si las variables miembro de las dos estructuras son exactamente iguales, son dos estructuras.
P.ej:

struct {
	char name[20];
	char sex[5];
	int age;
	char number[10];
}x;
struct {
	char name[20];
	char sex[5];
	int age;
	char number[10];
}*p;

int main()
{
	p = &x;
	return 0;
}

El código anterior se puede ejecutar cuando se compila, pero habrá advertencias.
 
 
 
3. Autorreferencia de estructura : La estructura contiene un miembro cuyo tipo es la estructura misma.

struct Node
{
	int data;
	//struct Node next;//这是一种错误的自引用
	struct Node *next;
};

Mira otro código:

typedef struct Node  //①
{
	int data;
	struct Node *next;//②
}node;  //③

Esto struct Noderedefine. Entre ellos, los significados de nodo de ① y ② son los mismos, y ③ es diferente de los otros dos.

Por ejemplo, tal redefinición es incorrecta.

typedef struct
{
	int data;
	Node *next;
}Node;

El programa informará un error:
Inserte la descripción de la imagen aquí
debido a que Node no ha completado la redefinición, no se puede utilizar primero en la estructura.

 
 
 
4. Estructura de alineación de la memoria

Hay alineación de memoria dentro de la estructura y la alineación de memoria afectará el tamaño general de la estructura.
La unidad básica de acceso de la computadora a la memoria es el byte, por lo que la computadora puede leer cualquier byte en la memoria a voluntad . Sin embargo, debido al diseño de hardware de la computadora, cuando la computadora lee datos, debe comenzar desde la posición inicial de los requisitos específicos.

 
 
① ¿Por qué la alineación de la memoria?
Debido al diseño del hardware, la eficiencia se reduce. Si accede a una memoria que no está alineada con la memoria, el procesador realizará múltiples accesos a la memoria.
② ¿Qué es la alineación de la memoria?
Sacrificar el espacio de la memoria para cumplir con las limitaciones del hardware de acceso a la memoria de la CPU y mejorar la eficiencia se denomina alineación de memoria.
La esencia de la alineación de la memoria: espacio para el tiempo.
③Cómo alinear la memoria:
las reglas de la alineación de la memoria:

1. El desplazamiento del primer miembro de la variable de estructura es 0.
2. Otras variables miembro deben alinearse con una dirección que sea un múltiplo entero de un cierto número (número de alineación).
3. El tamaño total de la estructura es un múltiplo entero de la alineación máxima (cada variable miembro tiene una alineación).
4. Cuando la estructura está anidada, la estructura anidada se alinea con un múltiplo entero del número máximo de bytes de alineación, y el tamaño total de la estructura es el número entero de todos los números de alineación máximos (incluido el número de alineación de la estructura anidada) Veces.
Por ejemplo:

struct stu{  //42 +2   4 
	char name[20];//20
	char sex[5];//5
	int age;//  3  +  4
	char number[10];//10
};

int main()
{
	printf("%d", sizeof(struct stu));
	return 0;
}

análisis:

char name[20];  大小为20 不需要对齐
char sex[5];    每一个元素大小为1字节,对齐数为1,可以整除  故大小为5
int age;  age为int型,对齐数为4,前面的字节数为25,不能整除,故有偏移量,偏移量为3
char number[10];每一个元素大小为1字节,对齐数为1,可以整除  故大小为10
上述总大小为:42。最大对齐数为:4.
不能整除4,故需进行扩大。为44

resultado:
Inserte la descripción de la imagen aquí

struct list  //32  最大对齐数:8  32
{
	char num[5];//5
	int add;// 3 +  4
	char *p;//4
	double prt;//8
	char opp;//1
	int div;// 3 + 4
};

int main()
{
	printf("%d\n", sizeof(struct list));
	return 0;
}

Inserte la descripción de la imagen aquí
El caso de la estructura anidada:

struct stu{  //50  最大对齐数:8   =  56
	char name[20];//20
	char sex[5];//5
	int age;//3 +  4
	double address;//8
	char number[10];//10
};

struct list  //81   最大对齐数:8   =  88  //这里的最大对齐数为什么是8?
{                                      //因为嵌套的结构体,最大对齐数为8,故,外部结构体最大对齐数也为8
	char num[5];//5
	int add;//  3  +  4
	char p;//1
	struct stu s;//3  +  56
	char opp;//1
	int div;// 3  +  4
	char mul;//1
};
int main()
{
	printf("%d\n", sizeof(struct stu));
	printf("%d\n", sizeof(struct list));
	return 0;
}

resultado:
Inserte la descripción de la imagen aquí

Por supuesto, el número de alineación también se puede modificar.

#pragma pack()

El número de alineación predeterminado se puede modificar.
Nota: El valor en () debe ser 1, 2, 4, 8, 16.
Como el código anterior: modificamos el número de alineación a 2:

#pragma pack(2)
struct list  
{
	char num[5];
	int add;
	char *p;
	double prt;
	char opp;
	int div;
};
int main()
{
	printf("%d\n", sizeof(struct list));
	return 0;
}

El número de bytes ha cambiado: 28.
Modificamos el número de alineación a 1:

#pragma pack(1)

El número de bytes ha cambiado: 26.
 
 
 
5. Segmento de bits: la declaración y la estructura del segmento de bits son similares, pero existen diferencias.

1. Los miembros del campo de bits deben ser int, unsigned int y con signo int
2. El nombre de miembro del campo de bits va seguido de dos puntos y un número

struct A
{
	unsigned char a : 2;
	unsigned char b : 3;
	unsigned char c: 6;
	unsigned char d;
	unsigned char e : 4;
};
int main()
{
	printf("%d\n", sizeof(struct A));
	return 0;
}

Inserte la descripción de la imagen aquí
Entonces, el tamaño de bytes de este código es de 4 bytes.
Probemos con esta tarea.

int main()
{
	struct A s;
	s.a = 4;
	s.b = 5;
	s.c = 6;
	s.d = 7;
	s.e = 8;
	return 0;
}

Análisis:
Inserte la descripción de la imagen aquí
Cuando se trata de un número con signo, debemos prestar atención a cuál es el bit de signo del bit más alto.

struct A
{
	char a : 2;
	char b : 3;
	char c: 6;
	char d;
	char e : 4;
};
int main()
{
	struct A s;
	s.a = 4;//100 发生截断00
	s.b = 5;//101 最高位为1,最后会原反补转换  结果为-3
	s.c = 6;//1100 
	s.d = 7;//1101
	s.e = 8;//1000  原反补转换  结果为-8
	printf("%d\n%d\n%d\n%d\n%d\n", s.a, s.b, s.c, s.d, s.e);
	return 0;
}

Inserte la descripción de la imagen aquí
Los segmentos pueden lograr un buen efecto de ahorro de espacio, pero existen problemas con la multiplataforma.
El campo de bits completo puede tomar la dirección, pero no puede tomarse solo.

 
 
 
 
Enumeración : la naturaleza del tipo de enumeración es int, y la condición predeterminada (se puede cambiar, tanto positiva como negativa) comienza desde 0 y aumenta secuencialmente.

La enumeración es un tipo y la verificación de tipos se realiza durante la compilación. Las macros se basan en el principio de sustitución y durante este proceso no se realizan comprobaciones.

enum Day
{
	MON,
	TUES,
	WED,
	THUR,
	FRI,
	SAT,
	SUN
};//一般都习惯于大写。(默认为常量)

Ventajas de la enumeración:

  1. Aumente la legibilidad y el mantenimiento del código
  2. En comparación con los identificadores definidos por macros, las enumeraciones tienen verificación de tipo y son más rigurosas.

 
 
 
 
Unión : Unión también es un tipo personalizado especial, que también contiene una serie de miembros, pero estos miembros comparten un espacio.

El tamaño de la unión no es la suma de todos los tipos.
En términos generales, el tamaño de la unión está determinado por el tamaño del elemento más grande de la unión. Después de la decisión, todos los elementos comparten espacio.
Cuando se usa union, solo se accede a un elemento a la vez.
La unión también debe considerar el problema de alineación de la memoria El tamaño final de la unión debe poder dividir el número máximo de alineaciones en la unión.

union un
{
	int i;
	char c[6];
};//该联合体字节大小为8

Los miembros del sindicato comparten un espacio de memoria común. Cambiar el valor de un miembro afectará el valor posterior.
Hay un ejemplo más práctico: ¿determinar el tamaño de la computadora actual?

union un
{
	int i;
	char c;
};

union un temp;
temp.i = 1;
printf("%d\n", temp.c);

Salida 0, almacenamiento big-endian, salida 1, almacenamiento little-endian.

Supongo que te gusta

Origin blog.csdn.net/w903414/article/details/106922417
Recomendado
Clasificación