2015-05-22 1 views
-1

Указатель в main(), ptrTop, инициализируется, чтобы указать на int topDeck = 1. Каждый раз, когда я запускаю программу, значение разыменованного указателя (я думаю) меняет свое значение на другое число. Я считаю, что проблема заключается в функции deal(). Если я прокомментирую вызов deal() в main(), значение моего указателя не будет изменено. Я не писал никаких утверждений, которые изменяют значение указателя. Я написал комментарии вокруг частей кода, которые могут иметь отношение к вопросу.Почему значение указателя изменяется после передачи его функции, которая не изменяет указатель?

/* 
* This is a card dealing program. 
* the fucntion deal() keeps changing the value of 
* the int pointer ptrTop declared in main(). sometimes, 
* the value is what it is sopposed to be (1), but when i run 
* the program again, it is a different value. I used 
* gcc (GCC) 4.9.2 20150212 (Red Hat 4.9.2-6) 
*/ 

int main(void) { 

    int topDeck = 1; 
    int *ptrTop = &topDeck; 

    //this ptrTop is sopposed to keep track of the last 
    //card dealt, but it randomly changes every time I run 

    unsigned int handSuit[5] = {0}; 
    unsigned int handFace[5] = {0}; 



    unsigned int deck[SUITS][FACES] = {0}; 


    deal(deck, face, suit, ptrTop, handSuit, handFace); 

    printf("%i\n", *ptrTop); 
    // If print the value while I comment out the deal() in line 55, 
    // the value of * ptrTop does not change. 
    // this gives me reason to believe that deal() is causing the trouble. 

} 


void deal(unsigned int wDeck[][FACES], const char *wFace[], const char *wSuit[], 
    int *ptrTop, unsigned int handSuit[], unsigned int handFace[]) 
{ 
    size_t card; 
    size_t row; 
    size_t column; 
    int top = *ptrTop; 
    // i have to use top because if i don't the dea() function will print 
    // more than 5 cards (it is sopposed to print a 5 card hand. 

    // these for loops loop through the double scripted array wDeck 
    for (card = top; card <= top + 4; ++card) { 

     for (row = 0; row < SUITS; ++row) { 

      for(column = 0; column < FACES; ++column) { 

       if(wDeck[row][column] == card) { 
        printf("%s of %s \n", wFace[ column ], wSuit[ row ]); 
        handFace[card] = column; 
        handSuit[card] = row; 
       } 
      } 
     } 
    } 
    // *ptrTop = card; 
    // the value of *ptrTop consistently becomes six if line above is uncommented. 
    // I would think that the value should still be 1 
    // when the program is run in this state. 
} 
+1

Так что кажется, что это не значение _ указателя pointer_, которое изменяется; скорее значение _что указывает указатель на_, правильно? – szczurcio

+3

Вы можете написать не более 10 строк кода, чтобы продемонстрировать ту же проблему. Узнайте, как создать минимальный, полный и проверенный пример. (Http://stackoverflow.com/help/mcve) –

+1

Адрес указателя никогда не изменяется, значение в этом адресе происходит, когда вы назначаете '* ptrTop = card;' –

ответ

3

Этот неясный контур является причиной:

for (card = top; card <= top + 4; ++card) 

карта получает индекс от 1 до 5, в то время как у вас есть переменные

unsigned int handSuit[5] = {0}; 
unsigned int handFace[5] = {0}; 

Это поддерживает только индекс 0 до 4. Вы можете получить доступ эти массивы вне границ, и как побочный эффект этого неопределенного поведения, вы перезаписываете другие переменные.

+0

Благодарю вас. –

0

Я не совсем уверен, что другое значение (чем шесть) из *ptrTop ожидаемых; давайте взглянем на deal:

for (card = top; card <= top + 4; ++card)

и помните, что это значение top как инициализируется в main:

int topDeck = 1; 
int *ptrTop = &topDeck; 

Так, в deal, вы петля пять раз, Инкрементирование card , то в последней итерации цикл for будет увеличивать card в пятый раз, см., что это 6, а так как 6 <= 5 является ложным, он уйдет, тогда, если вы сделаете *ptrTop = card;, *ptrTop действительно будет последовательно равен шести.

Смежные вопросы