簡體   English   中英

C 將 void 指針數組傳遞給 function

[英]C pass void pointer array to function

我想將一個 void 指針數組傳遞給 function 填充它的結果它與integer一起工作正常,但我在返回char*時遇到了麻煩

int function(void *arr[]);
int main(void) {
    void *arr[3];
    function(arr);
    printf("%d\n", *(int *)&arr[0]);
    printf("%d\n", *(int *)&arr[1]);
    printf("%s\n", (char *)&arr[2]);
}
int function(void *arr[]){
    arr[0] = (void*)(int)4;
    arr[1] = (void*)(int)6;
    char* test = "abc";
    arr[2] = (void*)test;
    return 0;
}

對於字符串,我沒有得到正確的值

arr的類型為void(*)[3]

arr[0]的類型為void* 它存儲適當轉換的值4的事實是無關緊要的。

&arr[0]的類型為void**

(int *)&arr[0]具有int*類型,但它指向void*類型的 object 而不是指向int類型的 object 。 這不是指針通常所做的。 可以擁有這樣的指針,但您可以合法地使用它的唯一方法是將其轉換回正確的類型,在本例中為void** 你沒有那樣做。

*(int *)&arr[0]的類型為int

在這里,您通過int類型的左值訪問void*類型的 object 。 這是未定義的行為。 不要那樣做。

如果要將arr[0]轉換回int ,只需執行以下操作:

printf("%d\n", (int)arr[0]);

同樣,如果要將arr[2]轉換回char* ,請執行以下操作:

printf("%s\n", (char*)arr[2]);

您可以傳遞一個void數組,並將該數組元素分配給動態分配的 memory 區域,該區域存儲指向的值。

#include <stdio.h>
#include <stdlib.h>
#include <string.h>

int function(void *arr[]){    
    arr[0] = malloc(sizeof(int));
    if (arr[0] == NULL) goto ERR_MALLOC_0;
    *(int*)arr[0] = 4;

    arr[1] = malloc(sizeof(int));
    if (arr[1] == NULL) goto ERR_MALLOC_1;
    *(int*)arr[1] = 6;

    const char *const test = "abc";
    arr[2] = malloc(strlen(test));
    if (arr[2] == NULL) goto ERR_MALLOC_2;
    strcpy(arr[2], test);

    return 0;

    // remember about error checking
    free(arr[2]);
    ERR_MALLOC_2:
    free(arr[1]);
    ERR_MALLOC_1:
    free(arr[0]);
    ERR_MALLOC_0:
    return -1;
}

int main(void) {
    void *arr[3];
    int err = function(arr);
    if (err == -1) abort();

    // & is the address of element, not it's element
    printf("%d\n", *(int*)arr[0]);
    printf("%d\n", *(int*)arr[1]);
    printf("%s\n", (char*)arr[2]);

    // remember to free memory
    for (int i = 0; i < 3; ++i) {
        // funny how we do not need to know the effective type
        free(arr[i]);
    }
}

但是這樣的 function 顯然是令人困惑的,並且會導致很多很多錯誤和問題。 而只是實際使用正確類型的變量:

#include <stdlib.h>
#include <string.h>

int function(int *val1, int *val2, char **string) {
    *val1 = 3;
    *val2 = 6;
    const char *test = "abc";
    *string = malloc(strlen(test));
    if (*string == NULL) return -1;
    strcpy(*string, test);
    return 0;
}

int main(void) {
    int val1; 
    int val2;
    char *string;
    int err = function(&val1, &val2, &string);
    if (err == -1) abort();

    printf("%d\n", val1);
    printf("%d\n", val2);
    printf("%s\n", string);

    free(string);
}

如果你真的想在不同的數據類型上實現一些虛擬表示和操作,那么使用普通的“ void指針數組”會讓你一事無成,因為這樣的數組不知道正在存儲的值的底層類型是什么 -作為程序員,您必須知道該數組中的內容(即arr[0]是一個intarr[2]是一個char* ),所以如您所知,您不妨只使用適當的變量從一開始的類型。

arr[0] = (void*)(int)4;

上述行將 integer 4 轉換為 void 指針(地址)並將其作為指針地址存儲在數組arr中。 我想這不是你想要的。

為了以您想要的方式使用 void 指針訪問數據,首先使其指向一個有效的 memory 地址,該地址將在 function 退出時保存數據。 You have to be careful while assigning memory address to a void pointer inside a function, all variables in that function's stack (local variables) will be popped off the from the stack when the function exits, making that memory addresses invalid. Only use static (or global) or dynamic memory while assigning the memory address to your pointer inside the function, if you want to use it outside the function.

暫無
暫無

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

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