Lenguaje C_0329 notas_estructura: estructura como parámetro de función/estructura de entrada scanf valor variable/matriz de estructura/estructura y estructura/anidamiento infinito

Tabla de contenido

11.2.2 Estructuras y funciones

estructura de entrada scanf

 Solución (1): variables temporales

Solución (2): puntero de estructura como parámetro (más recomendado)

11.2.3 Estructura dentro de estructuras

conjunto de estructuras

estructura dentro de la estructura

 Estructuras anidadas (rectángulos definidos por dos puntos diagonales)

 conjunto de estructuras dentro de estructuras 


11.2.2 Estructuras y funciones

Los tipos de datos como int y float se pueden usar como parámetros de funciones, y las estructuras también se pueden usar como tipos de datos (como se mencionó anteriormente)

int NúmeroDeDías(fecha de estructura d)

  • La estructura completa se puede pasar a la función como el valor del parámetro. 
  • En este momento, se crea una nueva variable de estructura en la función y se copia el valor de la estructura de la persona que llama.
  • El valor de retorno también puede ser una estructura.
  • (Las características anteriores son completamente diferentes de las matrices)

ejemplo


 //求明天的日期
#include<stdio.h>
#include<stdbool.h>
//定义了一个 结构 类型,里面包含三个int类型的变量 
struct date{
    int month;
    int day;
    int year;
};
 
bool isLeap(struct date d);//判断是否是闰年函数
int numberOfDays(struct date d);//给出每个月有几天的函数
 
int main()
{
    struct date today;
    struct date tomorrow;
 	int sig=1;
    printf("Enter today's date (mm dd yyyy):");
    scanf("%i %i %i",&today.month,&today.day,&today.year);
//%i是旧写法,和%d一样是输出十进制整数的格式控制符
//&today.month是先进行点运算,取成员month,再将输入的数据用&取地址。
    //因此点运算优先级高
 
 
//若今天不是本月最后一天(也就是本月的天数)
//明天就是天数加一
//	printf("today mm %d\n",today.month);
	//printf("这个月有%d天\n",numberOfDays(today));//这个月有32764天
if(today.day > numberOfDays(today) ||
	today.month >12 ){
		sig =0;
	printf("非法输入,请检查输入是否正确");
	
}
if(today.day != numberOfDays(today)){
    tomorrow.day = today.day+1;
    tomorrow.month = today.month;
    tomorrow.year = today.year;
//12月的最后一天,那么第二天就是第二年
}else if(today.month == 12){
    tomorrow.day = 1;
    tomorrow.month = 1;
    tomorrow.year = today.year+1;
}else{
//不是12月,而且今天是本月最后一天,明天就是下个月第一天
    tomorrow.day = 1;
    tomorrow.month = today.month+1;
    tomorrow.year = today.year;
}
if (sig){
	printf("Tomorrow's date is %i-%i-%i.\n",
    tomorrow.month,tomorrow.day,tomorrow.year);
}
 
return 0;
}
int numberOfDays(struct date d) //给出每个月有几天的函数
{
    int days=0;
    const int daysPerMonth[12]={31,28,31,30,31,30,31,31,30,31,30,31};
 	//printf("函数中的月份 %d\n",d.month); // 3
 	//printf("daysPerMonth[d.month-1]: %d\n",daysPerMonth[d.month-1]); //31
    if(d.month == 2 && isLeap(d))//【if语句里面 判断相等!!一定要用==啊啊啊】 
        days = 29;
    else{
    	days = daysPerMonth[d.month-1]; 
		//因为数组下标从0开始,month.1对应数组【0】
	}
       //printf("days %d\n",days); 
    return days;//单一出口
}
 
bool isLeap(struct date d)
{
    bool leap = false;
    if((d.year%4 == 0 && d.year%100 != 0)|| d.year%400 == 0)
        leap = true;
        //符合条件为闰年
return leap;
}

//Las variables de estructura se pueden pasar directamente entre funciones

bool isLeap(struct date d); //Juzga si es un año bisiesto function
int numberOfDays(struct date d); //Da la función del número de días en cada mes

estructura de entrada scanf

  • No existe un carácter de control de formato directamente correspondiente a un tipo de estructura completo, porque contiene varios tipos de datos definidos por el usuario.
  • Si tiene la intención de utilizar una función para leer la estructura, como por ejemplo:
  • #include<stdio.h>
    struct point{
        int x;
        int y;  };
     
    void getStruct(struct point);
    void output(struct point);
    void main(){
        struct point y = {0,0};
        getStruct(y);
        output(y);
    }
     
    void getStruct(struct point p){
    //接收到y结构变量的值,是另外一个结构变量
    //因此执行完这个程序后,y不会改变,output函数输出0,0
        scanf("%d",&p.x);
        scanf("%d",&p.y);
        printf("getstruct:%d,%d\n",p.x,p.y);
    }
    void output(struct point p){
        printf("output:%d,%d\n",p.x,p.y);
    }

 Resultado: (el valor en main no cambia), pero debido a que la función pasada es un clon de la estructura externa , no un puntero al contenido

 Solución (1): variables temporales

 La idea anterior de usar una función para leer la estructura es buena, pero dado que lo que se pasa a la función es un clon de la estructura externa, no un puntero al contenido, hay una manera:

En la función entrante, cree una variable de estructura temporal y luego devuelva la estructura temporal a la persona que llama

#include<stdio.h>
struct point{
    int x;
    int y;  };
 
struct point getStruct(void);
void output(struct point);
 
int main()
{    
    struct point y = {0,0};
    y = getStruct();//这个函数不需要传入参数
//结构之间可以直接赋值,将临时结构p赋给y
    output(y);
}
 
//一个返回类型为结构的函数
struct point getStruct(void)//这个函数不需要传入参数 但是它返回一个结构类型 
{
    struct point p;
    scanf("%d",&p.x);
    scanf("%d",&p.y);
    printf("getStruct: %d,%d\n",p.x,p.y);
    return p;//但是它返回一个结构类型 
}
 
void output(struct point p){
    printf("output: %d,%d\n",p.x,p.y);
}

Solución (2): puntero de estructura como parámetro (más recomendado)

 Cuando pasa una estructura grande a una función, pasar un puntero es más eficiente que copiar . Debido a que la forma en que C transfiere estructuras es por valor, se necesita espacio y tiempo para crear una estructura en la función llamada que sea exactamente igual a la exterior.

Existe una notación más sencilla para representar los miembros de la variable de estructura a la que apunta el puntero : ->

struct date{int mes; int día; int año;} myday; //Se declara el tipo de estructura y se crea la variable de estructura

struct date *p = &myday; //Saca la dirección de myday y dásela al puntero p

——Miembro (mes) en la variable de estructura (myday) señalada por el puntero——

(*p).mes = 12; //Escribiendo 1

p->mes = 12; //Escribiendo 2, en chino se llama el mes señalado por p

Conociendo este método de escritura simplificado, el programa de la solución 1 se puede escribir como:

#include<stdio.h>
struct point{
    int x;
    int y;  };

//函数的参数和返回类型现在都是结构指针
struct point* getStruct(struct point*);//传入指针  返回指针 
void output(struct point);//传入结构变量 
void print(const struct point *p);//传入结构指针(常量) 
 
int main()
{    
    struct point y = {0,0};
    getStruct(&y);//int *p=&a; 得到p(指向输出的xy) //getstruct函数返回的是指针p 也就是地址
    output(y);
    output(*getStruct(&y));
//output函数对其进行了*运算(地址上面的值)
//最后用%d 输出 printf函数拿出了地址 所以要用->指向指针p对应的地址
//才能用%d输出
/************************************************************************************************ */
//这里的参数意义:
//*代表了他要取出指针指向的变量,而此时指针指向的是另一个函数的返回值
//所以实际上传入的参数就是上一个函数的返回值
    print(getStruct(&y)); //getStruct得到的指针 传给print print继续操作 
//还可以做的是:
	*getStruct(&y) = (struct point){1,2};
//为什么?因为左边实际上是个变量,这完全符合编译规则和语法
}
 
//传入指针操作之后又返回,好处是可以在之后继续调用这个指针
struct point* getStruct(struct point *p) //返回指针 struct point * 参数指针 
{
    scanf("%d",&p->x); //取p所指的y的x
    scanf("%d",&p->y); //取p所指的y的y
    printf("getStruct:%d,%d\n",p->x,p->y);
    
    return p;
    //返回得到的参数p
}
 
	void output(struct point p){
	    printf("output:%d,%d\n",p.x,p.y);
	}
	 
	void print(const struct point *p)
	{
	//由于只进行输出,传入指针可以是const
	    printf("print: %d %d",p->x,p->y);
	}

11.2.3 Estructura dentro de estructuras

conjunto de estructuras

Se define una matriz y cada unidad de la matriz es una variable definida por mí.

int a[100] //Tipo básico

tiempo de estructura a[100] //tipo declarado por ti mismo

ejemplo:

struct date dates[100];
//定义了一个结构数组,100字节大小的数组,每一个单元都是一个结构变量
struct date dates[]={
    {4,5,2005},//dates[0]
    {2,4,2005} //dates[1]
};
 
//调用内部数据:
printf("%i",dates[0].day);

printf("%.2f");

Indica salida en tipo real (también tipo punto flotante) y retiene dos decimales. Si no hay dos decimales después del punto decimal, se representa por 0 o un número aleatorio. Si excede dos dígitos, se redondea.

estructura dentro de la estructura

Una variable de estructura puede ser un tipo de variable básica o una variable de estructura

struct dateAndTime{
    struct date sdate;
    struct time stime;
};

 Estructuras anidadas (rectángulos definidos por dos puntos diagonales)

struct point{
    int x;
    int y;
};
 
struct rectangle{
    struct point p1;
    struct point p2;
};
 
int main()
{
    struct rectangle r;
}
就可以有r.p1.x、r.p1.y、r.p2.x、r.p2.y等
来表示每个点
 

Si existe
    una estructura rectangular r,*rp;
    rp = &r;,

hay cuatro formas equivalentes :

  1. r.p1.x saca la x de p1 en r
  2. rp->p1.x x en p1 señalado por rp
  3. (r.p1).x No importa si agrega paréntesis o no, porque el operador de punto funciona de izquierda a derecha.
  4. (rp->p1).x Igual que arriba, porque el puntero apunta a él primero y luego se recupera la estructura.
  5. Pero no existe rp->p1->x (porque p1 no es un puntero, es una estructura y, por supuesto, no puede apuntar a nada más)

 conjunto de estructuras dentro de estructuras 

Matrioska ilimitada:

#include<stdio.h>
 
struct point{
    int x;
    int y;
};
struct rectangle{
    struct point p1;
    struct point p2;
};
 
void printRect(struct rectangle r)
{
    printf("<%d,%d> to <%d,%d>\n",
    r.p1.x, r.p1.y, r.p2.x, r.p2.y);
}
 
int main()
{
    int i;
    struct rectangle rects[]=
    {    {
   
   {1,2},{3,4}},//{ 1 2, 3 4} 12是p1 34是p2
         {
   
   {5,6},{7,8}}
    }
//rects[0].p1.x和y == {1,2}
//rects[0].p2.x和y == {3,4}
 
    for(i=0;i<2;i++)
    printRect(rects[i]);
 
return 0;
}

Supongo que te gusta

Origin blog.csdn.net/Shmily_as33/article/details/129835939
Recomendado
Clasificación