2017-11-19 4 views
0

整数の配列を読み込んでポインタとして返す関数を定義しました。ユーザ入力から配列を読み込む関数はガベージ値を返します

1 
5242692 
1474139472 
872394811 
-2 

これがなぜ起こるか私は理解することはできません。

1 
2 
3 
4 
5 

このプログラムは、このようなものを出力します。

#include "stdafx.h" 
#include <stdio.h> 

const int size = 5; 

int* getInput(); 
int main(int argc, _TCHAR* argv[]) 
{ 
    int* a = getInput(); 
    for(int i = 0; i < size; i++){ 
     printf("%d \n", a[i]); 
    } 
    return 0; 
} 

int* getInput(){ 
    int input[size]; 
    for(int i = 0; i < size; i++){ 
     scanf("%d", &input[i]); 
    } 
    return input; 
} 

問題は、の入力であることです。誰もこの問題で私を助けることができますか?

+0

GetInputの配列がスタックに割り当てられているため、ポインタを返すことはできません。あなたはmallocを使う必要があります。 – perreal

答えて

3

getInput()は、自動記憶域を持つローカル配列のアドレスを返します。関数が返すとこのオブジェクトにアクセスすると、未定義の動作が発生します。あなたが観察するのは、printfによって上書きされている配列の内容です。それは、それ自身のローカル変数に同じスペースを使用するからです。この動作は定義されていません。つまり、プログラムの失敗を含む何かが起こる可能性があります。

また、特にsizeなどの単純な名前でグローバル変数を定義することは避けてください。

あなたは、コピー先の配列と要素のその数渡す必要があります。

#include <stdio.h> 

int getInput(int *dest, int size); 

int main(int argc, char *argv[]) { 
    const int size = 5; 
    int input[size]; 

    int n = getInput(input, size); 
    for (int i = 0; i < n; i++) { 
     printf("%d\n", a[i]); 
    } 
    return 0; 
} 

int getInput(int *dest, int size) { 
    int i; 
    for (i = 0; i < size; i++) { 
     if (scanf("%d", &input[i]) != 1) 
      break; 
    } 
    /* return the number of integers successfully read from stdin */ 
    return i; 
} 
1

機能の配列を - それが機能終了時に寿命が終了します。期待することをするには、メモリを割り当てて返す必要があります。それは生涯がプログラムが終わるかあなたが解放するまで続くからです。

あなたは何をしたいかもしれません:あなたのケースでは

int *input = malloc(sizeof *input *size); 
if(input == NULL) 
{ 
    // error 
} 

.. 
return input; 

あなたがスコープ外にある変数にアクセスすることにより、未定義の動作を起動されています。

int* getInput(){ 
    int *input = malloc(sizeof *input *size); 
    if(input == NULL) 
    { 
     fprintf(stderr,"%s","Error in allocation"); 
     exit(1); 
    } 
    for(size_t i = 0; i < size; i++){ 
     scanf("%d", &input[i]); 
    } 
    return input; 
} 

あなたがmallocを使用して取得し、割り当てられたメモリは、メモリリークを回避するために解放する必要があります。あなたはそれを使って作業を終えたときにそれを行うことができます。

main()では、メモリを解放するだけです。ここでは代わりに、関数に渡すとメモリの異なる量を配分し、それに応じてユーザからの入力を取得することができますsize定数変数を使用しての

int main(int argc, _TCHAR* argv[]){ 
    ... 
    ... 
    free(a); 
} 

sizeの値が大きい場合は、sizeの値を関数に渡すことができます。

戻り値scanf()を確認することをお勧めします。だから、それへの呼び出しが

if(scanf("%d",&input[i])== 1) 
    // ok 

する必要がありますあなたは、詳細な議論hereを確認することができます。

関連する問題