मैं कठिनाई में आ रहा हूं यह समझने की कोशिश कर रहा हूं कि कैसे सी कंपाइलर एक छायादार तरीके से चरित्र सरणी, तार, पूर्णांक और सरणी की व्याख्या करता है। और मेरी मदद करने के लिए धन्यवाद। यहां तक ​​​​कि कई रेडिट उपयोगकर्ताओं ने बताया कि सी में पूरी पॉइंटर चीज इस बात पर थोड़ी छायादार है कि यह वास्तव में कमांड की व्याख्या कैसे करती है। इसलिए, मैं malloc को एक उदाहरण से समझने की कोशिश कर रहा हूं। लेकिन इससे पहले मैं यही समझता हूं। कहो *p एक चर है। फिर p वह पता रखता है जिसकी ओर वह इशारा कर रहा है। और *p पते के मान को संदर्भित करता है। गतिशील आवंटन के मामले में, जब मैं करता हूं

int *p = (int *)malloc(sizeof(int)*5); //say we want 5 locations //

और मैन्युअल रूप से लूप जैसा कि उपयोगकर्ता सभी 5 मानों में देता है, मैं जैसे मानों में डालता हूं:

scanf("%d", p+i) // as p already holds address, I get that we don't have to provide the & . And i being the iterator.. //

और फिर इसे दूसरे लूप के साथ प्रिंट करें यहाँ क्या होता है और मुझे कोई सुराग नहीं है कि क्यों।

मान लें कि उपयोगकर्ता इनपुट 55,66,77,88,99

जब मैं इस कोड का उपयोग करके प्रिंट करता हूं,

printf("%d", *p+i); // De-referencing the values in location p by using asterics, + the value of iteration,i //

मुझे 55,56,57,58,59 . के रूप में पागल मान मिलते हैं

तो इंटरनेट से थोड़ी मदद से, मैंने इस तरह से प्रिंटफ कोड की कोशिश की और यह एक आकर्षण की तरह काम किया, लेकिन मुझे डी-रेफरेंस भी नहीं करना पड़ा। यह इतना भ्रमित क्यों है?

printf("%d", p[i]); // No asterics used. How does the compiler know I want the value and not the address? as p only should hold the addresses, and *p should give us the values in those addresses //

इसके अलावा, किसी तरह अगर मैं printf("%d", *p++); करता हूं फिर यह भी काम करता है। मुझे क्यों नहीं मिल रहा है कि सी कैसे काम करता है?

उसी नोट पर, अगर मैं ऐसा ही करने की कोशिश करता हूं लेकिन इस बार scanf("%d", p[i]); के साथ, तो सिंटैक्स त्रुटि। मेरा मतलब है क्यों?

धन्यवाद ...

1
C0DEV3IL 19 जुलाई 2020, 08:51

2 जवाब

व्यंजक p[i] बिल्कुल *(p + i) के बराबर है - एक प्रारंभिक पता दिया गया p, i'वें ऑब्जेक्ट के पते की गणना करें (बाइट नहीं) !) उस पते के बाद और परिणाम को कम करना।

आप * ऑपरेटर का उपयोग नहीं करते क्योंकि सबस्क्रिप्ट ऑपरेशन में एक अंतर्निहित डीरेफरेंस है।

*p + i, p[0] + i लिखने के बराबर है - आप p का अनादर करते हैं और परिणाम में i का मान जोड़ते हैं, यही कारण है कि आपको अनुक्रम 55, 56, 57, 58, 59 मिला जब आप 55, 66, 77, 88, 99 की अपेक्षा कर रहे थे।

जब आप ऐरे नोटेशन का उपयोग करते हैं तो जीवन आसान हो जाता है - बस p[i] लिखें जब आप अनुक्रम में i'वां ऑब्जेक्ट चाहते हैं।

1
John Bode 19 जुलाई 2020, 16:22

मुझे लगता है कि एक छोटा रननेबल कोड मुझे समझाने से बेहतर समझने में आपकी मदद करेगा।

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

int main() {
    int *p = (int *)malloc(sizeof(int)*5);
    int *q = (int *)malloc(sizeof(int)*5);
    int i = 0;
    int test_val = 100;

    for(i = 0; i < 5; i++) {
        *(p + i) = test_val;
        q[i] = test_val;
        test_val = test_val + 10;
    }

    for(i = 0; i < 5; i++)
        printf("p[%d] = %d\n", i, p[i]);

    printf("p[i] gives the value in array p at index i \n\n");

    for(i = 0; i < 5; i++)
        printf("q[%d] = %d\n", i, q[i]);
    
    printf("Note that the values in p and q are equal which means that *(x + 1) and x[i] are 2 ways to access the same values \n\n");

    for(i = 0; i < 5; i++)
        printf("*p + %d = %d\n", i, *p + i);

    printf("*p + i gets value pointed by p and adds i to it in each iteration \n\n");

    for(i = 0; i < 5; i++)
        printf("*(p + %d) = %d\n", i, *(p + i));

    printf("*(p + i) gets value pointed by p + i \n\n");

    int *j = (int *)malloc(sizeof(int)*5);
    int *k = (int *)malloc(sizeof(int)*5);
    int *l = (int *)malloc(sizeof(int)*5);

    for(i = 0; i < 5; i++) {
         j[i] = test_val;
         k[i] = test_val;
         l[i] = test_val;
    }
    printf("(*j)++ = %d\n\n", (*j)++);
    printf("*(k++) = %d\n\n", *(k++));
    printf("*l++ = %d\n\n", *l++);
    
    for(i = 0; i < 5; i++) {
         j[i] = test_val;
         k[i] = test_val;
         l[i] = test_val;
    }
    printf("test_val = %d\n\n", test_val);
    printf("++(*j) = %d\n\n", ++(*j));
    printf("*(++k) = %d\n\n", *(++k));
    printf("*++l = %d\n\n", *++l);
    return 0;
}

निम्नलिखित आउटपुट है:

p[0] = 100
p[1] = 110
p[2] = 120
p[3] = 130
p[4] = 140
p[i] gives the value in array p at index i 

q[0] = 100
q[1] = 110
q[2] = 120
q[3] = 130
q[4] = 140
Note that the values in p and q are equal which means that *(x + 1) and x[i] are 2 ways to access the same values 

*p + 0 = 100
*p + 1 = 101
*p + 2 = 102
*p + 3 = 103
*p + 4 = 104
*p + i gets value pointed by p and adds i to it in each iteration 

*(p + 0) = 100
*(p + 1) = 110
*(p + 2) = 120
*(p + 3) = 130
*(p + 4) = 140
*(p + i) gets value pointed by p + i 

test_val = 150

(*j)++ = 150

*(k++) = 150

*l++ = 150

test_val = 150

++(*j) = 151

*(++k) = 150

*++l = 150

स्कैनफ प्रश्न के लिए, स्कैनफ को हमेशा एक पैरामीटर के रूप में एक सूचक की आवश्यकता होती है। p[I] (p + i) पर मान है और इस प्रकार गलत है। आदर्श रूप से, आपको scanf("%d", &(p[i])) का उपयोग करना चाहिए

0
Ajay Nair 19 जुलाई 2020, 09:27