與struct相關的宏定義(成員變數位移和擷取struct起始地址)

來源:互聯網
上載者:User

學過C語言的人都知道,我們可以通過struct定義自己的資料集合,從而實現對資料的封裝功能。

在實際的項目實踐中,struct定義的結構隨處可見。使用struct並不難,網上也有很多介紹struct的文章。

從如構定義到如何使用,講得很詳細。在此我就不多講。

這裡主要介紹在struct中如何擷取成員變數的位移以及通過成員變數的地址擷取struct的起始地址。

第二個問題是緊密依賴第一個問題的。

1. 擷取成員變數的位移。

直接上代碼吧:

#define offset_of(type, field) ( (unsigned int)&(((type *)(0))->field) )

這個宏對於剛開始學習C語言的人來說是比較困難的。

要理解這個宏,首先要理解宏定義到底是怎麼一回事,還有struct是怎麼一回事,還有指標的用法。

簡單解釋一下這個宏:

如果我們定義一個struct:

typedef struct{

int a;

int b;

} A;

那麼offset_of(A, b)就會輸出b相對於起始地址的位移。

& -- 這是取地址符號,表示擷取當前變數的地址。

0 -- 這是這個宏中最核心的地方。我們知道,對於一個struct, 比如說上面的A,  &A->b代表了b的地址, 如果我們想得到b相對於A的位移,那麼&A->b - &A就可以得到。

       但如是&A就是0呢。那麼&A->b不就是位移了嗎。

好了,當我們有了擷取成員變數相對位移的宏。如果已知成員變數的地址,那我們也可以輕鬆得擷取該成員所在結構體的首地址。

代碼如下:

#define container_of(ptr, type, field) (type *)((char *)ptr - offset_of(type, field))
我們只需要把該成員變數的地址減去你相對於首地址的位移,不就是該結構體的首地址了麼。

好了,不多說了,結出一個完整的執行個體:

// testConsole.cpp : Defines the entry point for the console application.//#include "stdafx.h"#include <time.h>#include <stdio.h>#include <stdlib.h>#define offset_of(type, field) ( (unsigned int)&(((type *)(0))->field) )#define container_of(ptr, type, field) (type *)((char *)ptr - offset_of(type, field))typedef struct{    int     a;    int     b;    char    c;    int     d;}package_t;int main(){    package_t pkg;    int *p;    p = (int *)&pkg.d;    printf("offset of 'd' is %d.\n", offset_of(package_t, d));    printf("The addr of pkg = 0x%x.\n", &pkg);    printf("The addr of d's container = 0x%x.\n", container_of(p, package_t, d));    return 0;}



聯繫我們

該頁面正文內容均來源於網絡整理,並不代表阿里雲官方的觀點,該頁面所提到的產品和服務也與阿里云無關,如果該頁面內容對您造成了困擾,歡迎寫郵件給我們,收到郵件我們將在5個工作日內處理。

如果您發現本社區中有涉嫌抄襲的內容,歡迎發送郵件至: info-contact@alibabacloud.com 進行舉報並提供相關證據,工作人員會在 5 個工作天內聯絡您,一經查實,本站將立刻刪除涉嫌侵權內容。

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.