再议指针变量和普通变量 最近我在看stm32单片机的freeRTOS内核源码程序里面使用了大量链表、结构体、结构体指针变量等随着看代码越来越多对指针变量尤其是结构体指针变量访问结构体成员有了一些新的认识现在记录下来。uint32_t ulTaskNotifyTake( BaseType_t xClearCountOnExit, TickType_t xTicksToWait ) { uint32_t ulReturn; taskENTER_CRITICAL(); { /* Only block if the notification count is not already non-zero. */ if( pxCurrentTCB-ulNotifiedValue 0UL ) { /* Mark this task as waiting for a notification. */ pxCurrentTCB-ucNotifyState taskWAITING_NOTIFICATION; if( xTicksToWait ( TickType_t ) 0 ) { prvAddCurrentTaskToDelayedList( xTicksToWait, pdTRUE ); traceTASK_NOTIFY_TAKE_BLOCK(); /* All ports are written to allow a yield in a critical section (some will yield immediately, others wait until the critical section exits) - but it is not something that application code should ever do. */ portYIELD_WITHIN_API(); } else { mtCOVERAGE_TEST_MARKER(); } } else { mtCOVERAGE_TEST_MARKER(); } } taskEXIT_CRITICAL(); taskENTER_CRITICAL(); { traceTASK_NOTIFY_TAKE(); ulReturn pxCurrentTCB-ulNotifiedValue; if( ulReturn ! 0UL ) { if( xClearCountOnExit ! pdFALSE ) { pxCurrentTCB-ulNotifiedValue 0UL; } else { pxCurrentTCB-ulNotifiedValue ulReturn - 1; } } else { mtCOVERAGE_TEST_MARKER(); } pxCurrentTCB-ucNotifyState taskNOT_WAITING_NOTIFICATION; } taskEXIT_CRITICAL(); return ulReturn; }1一个函数内部的变量可以分为两大类普通变量指针变量。无论一个变量多么复杂都是属于这两大类中的一个。2指针变量的尝试就是存储某个变量的地址它的目的是为了访问实现读写操作目的变量提供一个“起始索引”。这里着重强调一些“起始索引”的含义类比想顺着一条线团来找仓库中一个事物无论需要寻找的事物在哪里多么难找都可以通过这个“起始索引”对应的线团线头捋着找到。3再次理解结构体指针变量访问结构体内部成员的运算符“-”以及结构体变量变量名访问内部成员的运算符“.”;这两个运算符都是双目运算符也就是这2个运算符前后都有变量。从空间上考虑-运算符首先就有2中提到的“起始索引”的含义汉语翻译为“指向”通过这个“起始索引”一条条找到对应结构体成员然后去访问它结构体成员变量与指针变量在“空间”上是不在一起的物理上不相邻可能隔着十万八千里但是通过指针变量加上运算符“-”就是能轻松找到而且计算机非常擅长这种寻址操作。通过结构体变量加上运算符“.”再加上成员变量名就可以访问内部成员结构体变量和内部成员变量在空间物理上是相邻的而且还是包含关系因此运算符“.”往往汉语翻译成“的”。结构体变量的结构体成员。运算符“.”前后都是普通变量。4三大结构顺序、选择、循环。函数内部从宏观上是属于顺序结构的局部是有小顺序、选择、循环组成的顺序结构式最重要最基本的结构之所以局部使用了选择是因为触发判断某些语句需要当某些条件满足的时候才顺序执行当某些条件不满足的时候就不执行或者条件判断当满足条件一顺序执行代码段1当满足条件二顺序执行代码2....。局部使用循环是因为某些语句需要循环执行多次次数循环或者某些语句需要条件循环多次条件循环顺序、选择、循环都是与自然中法则是对应的自然界也是分为这三种结构。