簡體   English   中英

從函數返回結構

[英]Returning a struct from function

我試圖了解如何從函數返回結構,但是我完全迷失了。

這是代碼:

void initialize_server(struct data host_port){

        printf(" Set IP Address (X.X.X.X): ");
        fgets(data.host, sizeof(data.host), stdin);
        strchomp(data.host);

        printf(" Set Port: ");
        fgets(data.port_inc, sizeof(data.port_inc), stdin);
        strchomp(data.port_inc);

        return data;
}

這是來自.h的代碼

struct data{
    char host[16];
    char port_inc[8];
};

void initialize_server(struct data host_port);

功能定義

您的函數定義使用void ,后者將函數定義為不返回任何內容 ,因此您的return語句無用(稍后將進行討論)。

結構的使用

此外,定義似乎有些破損。 你寫:

void initialize_server(struct data host_port) {

然后在函數中編寫諸如data.host類的data.host 我假設您在某處具有datastruct定義,並且host_portstruct data類型的變量。

要創建struct some-struct-name類型的變量,您可以編寫struct some-struct-name your-variable-name 所以在你的代碼中

struct data {
    char host[SIZE];
    port_inc[SIZE];
}

定義了新的復合數據類型的布局。 類型由名稱data標識。 要創建這種類型的變量,您可以如下聲明它們:

struct data my_new_data_struct;  // A data structure on the stage of type
struct data *my_new_data_struct; // A pointer to data structure that 
                                 // would normally be allocated on the heap

可能的解決方案

使用按值傳遞的結構

您可以按以下方式編寫函數以返回結構,但效率不高,因為通過返回結構,您可能不得不利用堆棧來返回數據,並且還使用堆棧來傳遞數據。函數的參數。 這稱為傳遞值

結構數據initialize_server(結構數據host_port)

然后替換所有data. 位與host_port.

void initialize_server(struct data host_port)
{
        printf(" Set IP Address (X.X.X.X): ");
        fgets(**host_port**.host, sizeof(**host_port**.host), stdin);
        strchomp(**host_port**.host);

        printf(" Set Port: ");
        fgets(**host_port**.port_inc, sizeof(**host_port**.port_inc), stdin);
        strchomp(**host_port**.port_inc);

        return **host_port**;
}

使用指針

更好的方法是按如下所示傳遞指向數據結構的指針:

void initialize_server(struct data *const host_port)

這將函數initialize_server定義為不返回任何內容,因此無論如何您都無需返回,因為host_port不是指針。 該函數將變為:

void initialize_server(struct data *const host_port)
{
        printf(" Set IP Address (X.X.X.X): ");
        fgets(data.host, sizeof(host_port->host), stdin);
        strchomp(host_port->host);

        printf(" Set Port: ");
        fgets(host_port->port_inc, sizeof(host_port->port_inc), stdin);
        strchomp(host_port->port_inc);
}

但是現在請注意,調用此函數時,必須傳遞一個指針! 因此,您可能會遇到以下情況:

void do_something( )
{
   struct data my_host_port;
   //do stuff
   initialize_server( &my_host_port); // NOTE: The ampersand!!
   // do stuff
}  

或者,您可以按照以下方式malloc()您的主機端口。

void do_something( )
{
   struct data *my_host_port = malloc(sizeof(struct data));
   //do stuff
   initialize_server(my_host_port); // NOTE: NO ampersand as my_host_port  now already a pointer!!
   // do stuff
   free(my_host_port); // NOTE: You must free() what you malloc()
}  

代碼中的一些問題

  • 函數的返回類型為void ,這意味着:不返回任何內容。 這必須是struct data

  • 里面的功能host_port.host有可能被用來代替data.host

  • 您需要返回host_port ,而不是datastruct data是類型, host_port是參數的名稱)。

解決方案

首先,對struct data使用typedef更容易:

typedef struct data {
    char host[16];
    char port_inc[8];
} data;

現在,可以將data用作類型而不是struct data

data initialize_server(data host_port){

    printf(" Set IP Address (X.X.X.X): ");
    fgets(host_port.host, sizeof(host_port.host), stdin);
    strchomp(host_port.host);

    printf(" Set Port: ");
    fgets(host_port.port_inc, sizeof(host_port.port_inc), stdin);
    strchomp(host_port.port_inc);

    return host_port;
}

甚至使用指針struct data作為參數,以避免復制整個結構:

void initialize_server(data *host_port){

    printf(" Set IP Address (X.X.X.X): ");
    fgets(host_port->host, sizeof(host_port->host), stdin);
    strchomp(host_port->host);

    printf(" Set Port: ");
    fgets(host_port->port_inc, sizeof(host_port->port_inc), stdin);
    strchomp(host_port->port_inc);
}

可以這樣稱為:

data dt;
initialize_server(&dt); // takes the address of dt

返回時, dt將包含修改后的值。

首先,數據是struct的名稱,就像int是類型的名稱一樣。 host_port是變量的名稱。 因此,請盡可能使用host_port而不是數據。其次,返回類型為void,而不是結構數據。 也改變它。

struct data initialize_server(struct data host_port){

        printf(" Set IP Address (X.X.X.X): ");
        fgets(host_port.host, sizeof(host_port.host), stdin);
        strchomp(host_port.host);

        printf(" Set Port: ");
        fgets(host_port.port_inc, sizeof(data.port_inc), stdin);
        strchomp(host_port.port_inc);

        return host_port;
}

也考慮寫作

struct data_struct {
    char host[16];
    char port_inc[8];
} data;

只要在函數中設置結構的所有字段,就可以從函數中刪除參數:

struct data initialize_server(){
        struct data host_port;
        printf(" Set IP Address (X.X.X.X): ");
        fgets(host_port.host, sizeof(host_port.host), stdin);
        strchomp(host_port.host);
//...

或通過指針傳遞它並在函數內部進行修改。

這是一個結構:

struct a_tag {
   char c;
   int i;
   char *w;
};

您可以聲明一個返回如下結構的函數:

struct a_tag  return_struct(void);

然后,您可以編寫如下內容:

int main() {
   struct a_tag a1;
   a1 = return_struct();
   return 0;
}

您已經定義了如下功能:

/* return_struct: return a struct by value (copied) */
struct a_tag return_struct(void) {
   struct a_tag a;
   a.c = 'Y';
   a.i = 88;
   a.w = "My dog has fleas";
   /* can return local auto storage, because it is copied */
   return a;
}

這是函數返回struct的基本概念。 希望能幫助到你。

首先,為了從函數返回變量,函數的返回類型必須類似於變量的類型。因此, void類型的函數不能返回任何內容。由於要返回struct ,將函數的原型更改為: struct data initialize_server(struct data host_port); 接下來,您不能返回類型,但要返回由該類型創建的對象。

所以寫return host_port;

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM