कैसे ठीक है ?: ऑपरेटर सी में काम करते हैं?


10

मेरा एक सवाल है, कंपाइलर निम्नलिखित कोड पर कैसे काम करता है:

#include<stdio.h>

int main(void)
{
  int b=12, c=11;
  int d = (b == c++) ? (c+1) : (c-1);
  printf("d = %i\n", d);
}

मुझे यकीन है कि क्यों परिणाम है नहीं कर रहा हूँ d = 11


1
आपको यकीन क्यों नहीं हो रहा है? आप और क्या उम्मीद करेंगे और क्यों?
गेरहार्ड

2
मुझे इसमें शामिल सटीक शब्दार्थ याद नहीं है, लेकिन आप अपरिभाषित व्यवहार को देख सकते हैं।
चेपनेर

3
नहीं, @chepner, चयनित विकल्प का मूल्यांकन करने से पहले एक टर्नरी की स्थिति का मूल्यांकन करने के बाद एक अनुक्रम बिंदु है। यूबी वेक्टर से बचने के लिए मुझे लगता है कि आप सोच रहे हैं।
जॉन बोलिंगर

हाँ, मुझे यकीन नहीं है कि मुझे लगा कि संकलक के पास कोई विकल्प होगा।
chepner

जवाबों:


6

में int d = (b == c++) ? (c+1) : (c-1);:

  • का मान c++वर्तमान मान है c। 11. अलग से, c12 तक बढ़ा हुआ है।
  • b == 11गलत है, क्योंकि b12 है।
  • चूंकि (b == c++)झूठा है, (c-1)प्रयोग किया जाता है। साथ ही, c12 की वेतन वृद्धि को इस बिंदु तक पूरा किया जाना चाहिए।
  • चूंकि c12 है, c-111 है।
  • d उस मूल्य के लिए आरंभिक है, 11।

5

सी स्टैंडर्ड के अनुसार (6.5.15 कंडिशनल ऑपरेटर)

4 पहले ऑपरेंड का मूल्यांकन किया जाता है; इसके मूल्यांकन और दूसरे या तीसरे ऑपरेंड (जो भी मूल्यांकन किया जाता है) के मूल्यांकन के बीच एक अनुक्रम बिंदु है। दूसरे ऑपरेंड का मूल्यांकन केवल तभी किया जाता है जब पहले की तुलना असमान से 0 से की जाती है; तीसरे ऑपरेंड का मूल्यांकन केवल तभी किया जाता है जब पहले की तुलना 0 के बराबर हो; परिणाम दूसरे या तीसरे ऑपरेंड (जो भी मूल्यांकन किया गया है) का मूल्य है, नीचे वर्णित प्रकार में परिवर्तित किया गया है। १०.१०)

तो इस घोषणा की प्रारंभिक अभिव्यक्ति में

int d = (b == c++) ? (c+1) : (c-1);

चर bकी तुलना चर के मूल्य से की जाती है cक्योंकि पोस्ट-इन्क्रीमेंट ऑपरेटर इसे बढ़ाने से पहले अपने ऑपरेंड का मान लौटाता है।

चूंकि मान एक-दूसरे के बराबर नहीं हैं ( b12 पर सेट है जबकि c11 पर सेट है) तो उप-अभिव्यक्ति (c-1)का मूल्यांकन किया जाता है।

उद्धरण के अनुसार ऑपरेटर की स्थिति के मूल्यांकन के बाद एक अनुक्रम बिंदु है। इसका अर्थ है कि स्थिति के मूल्यांकन के बाद चर में पोस्ट-इन्क्रीमेंट ऑपरेटर को लागू करने के बाद cमूल्य है । परिणामस्वरूप चर d को मान ( ) द्वारा प्रारंभ किया जाता है ।12c112 - 1


2
एकमात्र सही उत्तर - इस विशिष्ट मामले में अनुक्रम बिंदु का उल्लेख करके उत्तर दिया जाना चाहिए ?:। क्योंकि सी में सामान्य रूप से, ++एक ही ऑपरेंड पर अन्य संचालन के साथ संयोजन अपरिभाषित व्यवहार है। और यह कोड केवल अनुमानित रूप से काम करता है क्योंकि ?:इसमें कई विशेष स्नोफ्लेक नियम हैं।
लुंडिन

4

शर्त गलत है, इसलिए falseमामला होगा: c-1लेकिन जब से आपने वेतन वृद्धि की हैc इस हालत मेंc++ , इसलिए cअब है 12। परिणाम इस प्रकार 12 - 1 है जो 11 है।

संपादित करें: क्या ओपी गलत समझा पोस्ट वृद्धि थी।

तो वास्तव में ऐसा क्या होता है:

#include<stdio.h>
int main(void)
{
  int b=12, c=11;
  int d;

  if (b == c) { // 12 == 11 ? -> false
    c = c + 1;
    d = c + 1;
  } else { // this executes since condition is false
    c = c + 1; // post increment -> c++ -> c = 12 now
    d = c - 1; // 12 - 1 = 11 -> d = 11
  }
  printf("d = %i\n", d);
}

1
मुझे लगता है कि ओपी c++हालत में देखते हुए ऑपरेशन के आदेश का हवाला दे रहा है । स्थिति झूठी है, लेकिन तब की गणना करने के लिए मूल मूल्य का cउपयोग किया जाता है c - 1, न कि वर्धित संस्करण।
चेपनेर

1
मैंने सोचा कि ईमानदार 12 == 11 + 1 यह सच है ...
12:11

लेकिन नए सी मूल्य का इस्तेमाल होने के बाद से यह सही नहीं है या क्या मैं आपकी बात याद कर रहा हूं?
एरकॉन

मुझे लगता है कि इसके बीच गलतफहमी हो सकती हैc++++c
चट्टरऑन

@ N00b c++, पोस्ट- इन्क्रीमेंट ऑपरेटर है। c++11 का मूल्य , बनाने के साइड इफेक्ट के साथ है c == 12++c12 का मान होगा
chepner

4

यदि आपका कोड इस तरह दिखाई देगा, तो एक नियमित रूप से अनुवादित:

int b=12, c=11;
int d;

if (b == c++)
   d = c+1;
else
   d = c-1;

यहाँ क्लू यह है कि हालत की जाँच के बाद c को बढ़ा दिया जाता है। तो आप elseराज्य में प्रवेश करते हैं लेकिन c का मूल्य पहले से ही 12 है।


1

को देखें टर्नरी ऑपरेटर ।

वाक्य - विन्यास

स्थिति ? value_if_true: value_if_false

तो, आपने लिखा

int d = (b == c++) ? (c+1) : (c-1);

इस स्थिति में, परिणाम 11 होगा क्योंकि, यदि चेक के बाद, 'c' मान बढ़ा हुआ है (c + 1 = 12) और उसके बाद ही यह c (12) -1 को 'd' मान सेट करता है, जो 11 है।

यदि आप उपयोग करते हैं, उदाहरण के लिए:

int d = (b == ++c) ? (c+1) : (c-1);

कथन की जाँच करने से पहले "c" मान बढ़ाया जाएगा, इसलिए यह सही होगा और "d" मान c (12) +1 होगा जो 13 है।

हमारी साइट का प्रयोग करके, आप स्वीकार करते हैं कि आपने हमारी Cookie Policy और निजता नीति को पढ़ और समझा लिया है।
Licensed under cc by-sa 3.0 with attribution required.