Друк значення покажчика зі збільшенням адреси в C

#include 
#include 

int main()
{
int k,*ptr=NULL;
int arr[]={1,2,3,4,5,6,7,8,9,10};
ptr=arr;
printf("%d ",*ptr++);
printf("%d ",*(ptr++));
printf("%d ",(*ptr)++);
printf("%d ",*++ptr);
printf("%d ",++*ptr);
}

Чому другий printf надрукує номер 2 ? Потрібно роздрукувати 3 .

0
Чому треба точно роздрукувати 3?
додано Автор Bartek Banachewicz, джерело
Ви робите пост-інкремент замість попереднього збільшення. Ось чому гарна ідея збільшити окремо від того, що ви хочете робити з додатковою змінною.
додано Автор user554546, джерело

7 Відповіді

Як і всі інші, це відмінність між попередньо збільшеними (там, де приріст відбувається до видобутку значення) і пост-інкремент (де виявлено значення, а потім відбувається приріст). Цінність 2, звичайно, повинна бути роздрукована.

Може бути, цей код, що підтверджує твердження, допоможе. Макрос assert() зупиняє програму, якщо вказана умова є помилковою, коли вона виконується. Затвердження не спрацьовують.

Затвердження показують, як змінюється значення ptr , а також як змінюються значення в масиві.

#include 
#include 

int main(void)
{
    int arr[] = {1,2,3,4,5,6,7,8,9,10};
    int *ptr = arr;

    assert(ptr == &arr[0]);
    printf("%d\n",*ptr++);     //print 1; ptr = &arr[1]
    assert(ptr == &arr[1]);
    printf("%d\n",*(ptr++));   //print 2; ptr = &arr[2]
    assert(ptr == &arr[2]);
    assert(*ptr == 3);
    printf("%d\n",(*ptr)++);   //print 3; ptr = &arr[2]; arr[2] = 4
    assert(ptr == &arr[2]);
    assert(*ptr == 4);
    printf("%d\n",*++ptr);     //print 4; ptr = &arr[3]
    assert(ptr == &arr[3]);
    assert(*ptr == 4);
    printf("%d\n",++*ptr);     //print 5; ptr = &arr[3]; arr[3] = 5
    assert(ptr == &arr[3]);
    assert(*ptr == 5);

    printf("Offset: %d\n", (int)(ptr - arr));
    for (int i = 0; i < 9; i++)
        printf("a[%d] = %d\n", i, arr[i]);
    return 0;
}

Вихід:

1
2
3
4
5
Offset: 3
a[0] = 1
a[1] = 2
a[2] = 4
a[3] = 5
a[4] = 5
a[5] = 6
a[6] = 7
a[7] = 8
a[8] = 9
1
додано
дякую вам за ваш час .. тепер я це добре розумію :)
додано Автор Waseem Gabour, джерело

Оператор post increment збільшує значення після variabl .

Таким чином, після отримання * ptr , тобто 2, ptr само покращується.

1
додано
@YuHao Ні, пріоритет постфікса ++ вище, ніж у оператора індіорієнта * . * ptr ++ і * (ptr ++) точно еквівалентні.
додано Автор Daniel Fischer, джерело
ах! так що його так само, як "* ptr + +" правильно? (), чи потрібно просто обдурити нас?
додано Автор Waseem Gabour, джерело

* ptr + + перше неперерахування покажчик, який дає 2, потім збільшує покажчик Вираз * (ptr ++) - це пост-інкрементне вираження, тому значення цього виразу є ptr, а потім його збільшують. Таким чином, результат виразу полягає в тому, що він все ще вказує на 2

0
додано

оператор * поширюється на результат p ++, що є значенням оригіналу p (до збільшення). Тому він друкує 2 . Я хочу, щоб ви надрукували 3 (++ p), що повертає збільшене значення.

0
додано

Це має друкувати 2, оскільки оператор postfix ++ спочатку повертає значення, а потім збільшує його. Те, що ви додали дужки навколо нього (* (ptr ++)), не впливає на приріст. Значення буде збільшуватись після всієї лінії.

Дивлячись на розбирання може допомогти вам побачити, що відбувається в цьому рядку.

0
додано

* ptr ++ повертає значення в ptr , а потім збільшує його, тому в другому операторі printf() він повертає 2, а потім збільшує його до 3

0
додано

Не, тому що ptr + + повертає значення ДО настання, тому значення 2.

0
додано
У цьому випадку так. * (ptr ++) -> increment ptr і повернути покажчик на дисплей "2", так що printf 2.
додано Автор Shar, джерело
ах! так що його так само, як "* ptr + +" правильно? (), чи потрібно просто обдурити нас?
додано Автор Waseem Gabour, джерело