C ++ में POD के प्रकार क्या हैं?


977

मैंने इस शब्द को कुछ समय POD- टाइप किया है।
इसका क्या मतलब है?



5
कृपया देखें चैट .stackoverflow.com/transcript/message/213026#213026 और अगले दिन के संदेशों के लिए स्वीकार किए गए उत्तर के बारे में चर्चा के लिए संदेश
जोहान्स स्काउब -


@ paxos1977: कृपया "समाधान" (वर्तमान में हेवगिल के उत्तर) के अपने चयन को बदल दें, ताकि एक मौलिक गलत जवाब गूगलेर्स को गुमराह न करे जो यहां समाप्त होते हैं।
चीयर्स एंड हीथ। - अल्फ

हमने निष्कर्ष निकाला है कि सी-स्टाइल स्ट्रिंग एक POD प्रकार नहीं है क्योंकि 1.) सूचक स्ट्रिंग डेटा के साथ सन्निहित नहीं है, और 2.) स्ट्रिंग को POD प्रकार बनाने के लिए, आपको टाइप सुनिश्चित करना होगा पीओडी प्रकार के पूर्वनिर्धारित आकार के भीतर इसमें एक शून्य-अवधि का चार्ट था, जो अपरिभाषित व्यवहार के लिए अग्रणी था।

जवाबों:


694

POD का मतलब प्लेन ओल्ड डेटा है - यानी, एक वर्ग (चाहे वह कीवर्ड structया कीवर्ड के साथ परिभाषित हो class) बिना कंस्ट्रक्टर्स, डिस्ट्रक्टर्स और वर्चुअल मेम्बर्स के काम करता है। POD पर विकिपीडिया का लेख थोड़ा और विस्तार में जाता है और इसे परिभाषित करता है:

C ++ में एक सादा पुराना डेटा संरचना एक समग्र वर्ग है जिसमें केवल PODS सदस्य होते हैं, जिसमें कोई उपयोगकर्ता-परिभाषित विध्वंसक नहीं होता है, कोई उपयोगकर्ता-निर्धारित प्रतिलिपि असाइनमेंट ऑपरेटर नहीं होता है, और पॉइंटर-टू-मेंबर प्रकार का कोई नॉनस्टैटिक सदस्य नहीं होता है।

इस विवरण में C ++ 98/03 के लिए ग्रेटर विवरण पाया जा सकता है । सी ++ 11 ने पीओडी के आसपास के नियमों को बदल दिया, उन्हें बहुत आराम दिया, इस प्रकार यहां एक अनुवर्ती उत्तर की आवश्यकता हुई


34
एक अंतर है। आंतरिक प्रकार "बिलियन" भाषा की प्रधानताएं हैं। POD प्रकार ये होते हैं, इन (और अन्य POD) के जोड़ एकत्रीकरण होते हैं।
एडम राइट

59
POD प्रकारों में ऐसी विशेषताएं होती हैं जो गैर-POD प्रकार नहीं होती हैं। उदाहरण के लिए, यदि आपके पास एक वैश्विक, कास्ट, POD- प्रकार की संरचना है, तो आप इसकी सामग्री को ब्रेस नोटेशन के साथ आरंभीकृत कर सकते हैं, इसे रीड-ओनली मेमोरी में डाल दिया जाता है, और इसे (कंस्ट्रक्टर या अन्यथा) को इनिशियलाइज़ करने के लिए किसी कोड की आवश्यकता नहीं होती है, क्योंकि यह प्रोग्राम इमेज का हिस्सा है। यह उन एम्बेडेड लोगों के लिए महत्वपूर्ण है जिनके पास अक्सर रैम, रोम, या फ्लैश पर तंग बाधाएं होती हैं।
माइक डीसिमोन

34
C ++ 11 में, आप यह बता सकते हैं कि क्या MyType POD है या नहीं।
अल्लौरकोड

7
C ++ प्रदर्शन पर बज़्ने स्ट्रॉस्ट्रुप की तकनीकी रिपोर्ट बताती है कि C ++ मानक एक POD को " एक डेटा प्रकार जो लेआउट, आरंभीकरण में C के समतुल्य डेटा प्रकार के साथ संगत है, और इसके मेमेकपी के साथ कॉपी किए जाने की क्षमता " के रूप में वर्णित करता है । शायद एक पीओडी प्रकार और एक पीओडी संरचना के बीच अंतर किया जाना चाहिए।
user34660

6
Lea1 यह उत्तर अभी भी मूलभूत रूप से गलत है और 16 अगस्त 2016 तक भ्रामक है: POD प्रकार केवल वर्ग प्रकार तक सीमित नहीं हैं।
चीयर्स एंड हीथ। - अल्फ

352

बहुत अनौपचारिक रूप से:

एक POD एक प्रकार है (कक्षाओं सहित) जहां C ++ कंपाइलर गारंटी देता है कि संरचना में कोई "जादू" नहीं होगा: उदाहरण के लिए vtables में छिपे हुए संकेत, ऑफ़सेट जो उस पते पर लागू होते हैं जब इसे अन्य प्रकारों में डाला जाता है। कम से कम अगर लक्ष्य का POD भी), कंस्ट्रक्टर या डिस्ट्रक्टर्स। मोटे तौर पर, एक प्रकार एक POD है जब इसमें मौजूद एकमात्र चीजें अंतर्निहित प्रकार और उनमें से संयोजन होती हैं। परिणाम कुछ ऐसा है जो "सी प्रकार" की तरह काम करता है।

अनौपचारिक रूप से कम:

  • int, char, wchar_t, bool, float, doubleफलियों, के रूप में कर रहे हैं long/shortऔर signed/unsignedउनमें से संस्करणों।
  • पॉइंटर्स (पॉइंटर-टू-फंक्शन और पॉइंटर-टू-मेंबर सहित) POD हैं,
  • enums POD हैं
  • एक constया volatileपॉड एक पॉड है।
  • एक class, structया unionफली की एक पॉड प्रावधान था कि सभी गैर स्थैतिक डेटा सदस्य हैं public, और यह कोई आधार वर्ग और कोई कंस्ट्रक्टर्स, विनाशकर्ता, या आभासी तरीकों है। स्थैतिक सदस्य इस नियम के तहत POD होने से कुछ नहीं रोकते हैं। यह नियम C ++ 11 में बदल गया है और कुछ निजी सदस्यों को अनुमति दी गई है: क्या सभी निजी सदस्यों के साथ एक वर्ग POD वर्ग हो सकता है?
  • विकिपीडिया यह कहना गलत है कि एक POD में टाइप पॉइंटर-टू-मेंबर के सदस्य नहीं हो सकते। या यों कहें, यह C ++ 98 शब्दांकन के लिए सही है, लेकिन TC1 ने स्पष्ट किया कि संकेत-सदस्य सदस्य POD हैं।

औपचारिक रूप से (C ++ 03 मानक):

3.9 (10): "अंकगणित प्रकार (3.9.1), एन्यूमरेशन प्रकार, पॉइंटर प्रकार और पॉइंटर से सदस्य प्रकार (3.9.2) और इन प्रकारों के सीवी-योग्य संस्करण (3.9.3) सामूहिक रूप से कॉलर स्केलर प्रकार हैं। स्केलेर प्रकार, POD- संरचना प्रकार, POD- संघ प्रकार (खंड 9), इस प्रकार के सरणियाँ और इन प्रकारों के cv- योग्य संस्करण (3.9.3) को सामूहिक रूप से POD प्रकार कहा जाता है "

9 (4): "A POD- संरचना एक समग्र वर्ग है जिसमें गैर-POD- संरचना, गैर POD- संघ (या इस प्रकार के सरणी) या संदर्भ का कोई गैर-स्थैतिक डेटा सदस्य नहीं है, और इसका कोई उपयोगकर्ता नहीं है- कॉपी ऑपरेटर और कोई उपयोगकर्ता-परिभाषित विध्वंसक परिभाषित नहीं करता है। इसी तरह एक POD- संघ एक समग्र संघ है जिसमें गैर-POD- संरचना, गैर-POD- संघ (या इस प्रकार के सरणी) या संदर्भ के प्रकार का कोई गैर-स्थैतिक डेटा सदस्य नहीं है, या और कोई उपयोगकर्ता-परिभाषित प्रतिलिपि ऑपरेटर और कोई उपयोगकर्ता-निर्धारित विध्वंसक नहीं है।

8.5.1 (1): "एक समुच्चय एक सरणी या वर्ग (खंड 9) है जिसमें कोई उपयोगकर्ता-घोषित निर्माता (12.1), कोई निजी या संरक्षित गैर-स्थैतिक डेटा सदस्य (क्लाज 11), कोई आधार वर्ग (खंड 10) नहीं है। और कोई आभासी कार्य नहीं (10.3)। "


3
आपके पास औपचारिक / कम औपचारिक है। आप अंगूठे का नियम जोड़ सकते हैं। बिल्ट इन टाइप्स (या ऐसा ही कुछ) के प्रकार और एकत्रीकरण में निर्मित। सटीक परिभाषा प्राप्त करने के अलावा, हमें ज्ञान का उपयोग करने के लिए आसान बनाने की आवश्यकता है।
मार्टिन यॉर्क

1
आप "offsets पर थोड़ा गलत हैं, जब एक और प्रकार" कास्ट करते हैं । आधार या व्युत्पन्न वर्ग के लिए कास्टिंग करते समय उन ऑफसेट को लागू किया जाता है। इसलिए, यदि आप POD बेस क्लास पॉइंटर से नॉन-POD व्युत्पन्न क्लास में जाते हैं, तो भी आप एक एडजस्टमेंट कर सकते हैं।
MSalters

1
@ सेव जेसोप: हमें पीओडी और गैर-पीओडी के बीच अंतर करने की आवश्यकता क्यों है?
लेज़र

6
@ लेज़र: यह एक अन्य प्रश्न है, "PODs कैसे व्यवहार करते हैं?" "POD का क्या अर्थ है?" के विपरीत। सारांश में अंतर इनिशियलाइज़ेशन से संबंधित है (इसलिए डुप्लिकेट ऑब्जेक्ट्स के लिए मेमकी का उपयोग भी), उस कंपाइलर के लिए सी स्ट्रक्चर लेआउट के साथ संगतता, और पॉइंटर अप और डाउन-कास्टिंग। PODs "C प्रकारों की तरह कार्य करते हैं", गैर-PODs ऐसा करने की गारंटी नहीं देते हैं। इसलिए यदि आप चाहते हैं कि आपका प्रकार C संरचना की तरह ही कार्य करे, तो आपको यह सुनिश्चित करना चाहिए कि यह POD है, इसलिए आपको अंतर जानने की आवश्यकता है।
स्टीव जेसोप

4
@muntoo: यह रहा है, वास्तव में मैं इस जवाब पर टिप्पणी कर रहा था कि विकिपीडिया से पुरानी जानकारी उद्धृत करता है। मैं उस जवाब को संपादित कर सकता हूं, मुझे लगता है, लेकिन मुझे परेशानी होती है, अगर मैं अन्य लोगों के जवाब को खदान से सहमत होने के लिए संपादित करता हूं, चाहे मुझे लगता है कि मैं कितना सही हूं।
स्टीव जेसोप

20

सादा पुराना डेटा

संक्षेप में, यह सब में निर्मित डेटा प्रकार (उदाहरण के लिए है int, char, float, long, unsigned char, double, आदि) और सभी पॉड डेटा का एकत्रीकरण। हाँ, यह एक पुनरावर्ती परिभाषा है। ;)

अधिक स्पष्ट होने के लिए, एक पीओडी वह है जिसे हम "एक संरचना" कहते हैं: एक इकाई या इकाइयों का एक समूह जो केवल डेटा संग्रहीत करता है।


12
यह सच है कि हम कभी-कभी उन्हें 'एक संरचना' कहते हैं। हालाँकि, हम ऐसा करना हमेशा गलत मानते हैं, क्योंकि एक संरचना आवश्यक रूप से एक POD- प्रकार नहीं है।
स्टीव जेसप

6
स्पष्ट रूप से ... संरचना और वर्ग लगभग समान हैं, लेकिन "व्यापार" में हम 'एक संरचना' को एक साधारण डेटा कलेक्टर कहते हैं, आमतौर पर बिना ctor और dtor के, आमतौर पर मूल्य शब्दार्थ के साथ ...
ugasoft

2
मेरे लिए यह सी + + गलत था, जो कि क्लास कीवर्ड के समान स्ट्रक्चर बनाने के लिए या करीब: स्ट्रक्चर ही क्लास में पब्लिक डिफॉल्ट एक्सेस जोड़ता है। मैं सी-लाइक स्ट्रक्चर्स बनाने के लिए सरल था और हमारे पास C ++ के दिन 0 पर पॉड्स होंगे।
user1708042

ugasoft: आपका उत्तर भ्रामक हो सकता है - आपकी टिप्पणी ने लापता विवरण को समझाया कि इसका उपयोग मानक के बजाय व्यवहार में किया जाता है। वाह, 8 साल, तुम यहाँ भी हो? ;-)
हुरोन

एक स्ट्रिंग के अपवाद के साथ क्योंकि आप इसे स्ट्रिंग की लंबाई निर्धारित करने के बिना मेमकीपी के साथ कॉपी नहीं कर सकते हैं।

12

जैसा कि मैं समझता हूं कि POD (PlainOldData) सिर्फ एक कच्चा डेटा है - इसकी आवश्यकता नहीं है:

  • निर्माण करने के लिए,
  • बरबाद होना,
  • कस्टम ऑपरेटरों के लिए है।
  • आभासी कार्य नहीं होने चाहिए,
  • और ऑपरेटरों को ओवरराइड नहीं करना चाहिए।

अगर कुछ POD है तो कैसे जांचें? खैर, वहाँ एक संरचना है कि कहा जाता है std::is_pod:

namespace std {
// Could use is_standard_layout && is_trivial instead of the builtin.
template<typename _Tp>
  struct is_pod
  : public integral_constant<bool, __is_pod(_Tp)>
  { };
}

(हेडर type_traits से)


संदर्भ:


2
गलत, एक POD प्रकार में सदस्य फ़ंक्शन या ओवरलोड ऑपरेटर हो सकते हैं। (लेकिन इसमें वर्चुअल मेंबर फ़ंक्शंस नहीं हो सकते।)
कॉलिन डी बेनेट

@ColinDBennett हाँ, यह सच है। गलतफहमी के लिए खेद है। Awser में संपादित / बाहर।
१५:१५ को

10

एक POD (सादा पुराना डेटा) ऑब्जेक्ट में इन डेटा प्रकारों में से एक है - एक मौलिक प्रकार, सूचक, संघ, संरचना, सरणी, या वर्ग - जिसमें कोई निर्माता नहीं है। इसके विपरीत, एक गैर-पीओडी वस्तु वह है जिसके लिए एक निर्माता मौजूद है। POD ऑब्जेक्ट अपने जीवनकाल की शुरुआत तब करता है जब वह अपने प्रकार के लिए उचित आकार के साथ भंडारण प्राप्त करता है और इसका जीवनकाल तब समाप्त होता है जब ऑब्जेक्ट के लिए स्टोरेज का पुन: उपयोग या डीलॉक्लेट किया जाता है।

PlainOldData प्रकारों में से भी कुछ नहीं होना चाहिए:

  • वर्चुअल फ़ंक्शंस (या तो उनके स्वयं के, या विरासत में मिले)
  • आभासी आधार कक्षाएं (प्रत्यक्ष या अप्रत्यक्ष)।

PlainOldData की शिथिल परिभाषा में निर्माणकर्ताओं के साथ ऑब्जेक्ट शामिल हैं; लेकिन उन लोगों को शामिल करता है जो आभासी कुछ भी करते हैं। PlainOldData प्रकार के साथ महत्वपूर्ण मुद्दा यह है कि वे गैर-बहुरूपी हैं। वंशानुक्रम POD प्रकारों के साथ किया जा सकता है, हालाँकि यह केवल ImplementationInheritance (कोड का पुन: उपयोग) के लिए किया जाना चाहिए न कि बहुरूपता / उपप्रकार के लिए।

एक आम (हालांकि सख्ती से सही नहीं) परिभाषा यह है कि प्लेनओल्डडेटा एक ऐसी चीज है जिसमें कोई वीटेबल नहीं है।


योर उत्तर बहुत अच्छा है, लेकिन इस प्रश्न ने 8 साल पहले उत्तर स्वीकार कर लिया है, साथ ही कई अन्य अच्छे उत्तर। आप SO को अधिक योगदान दे सकते हैं यदि आप ज्ञान का उपयोग उन प्रश्नों के उत्तर देने के लिए करते हैं जो अभी तक उत्तर नहीं दिए गए हैं)))
mvidelgauz

10

हमें POD और गैर-POD के बीच अंतर करने की आवश्यकता क्यों है?

C ++ ने अपने जीवन की शुरुआत C के विस्तार के रूप में की। जबकि आधुनिक C ++ अब C का एक कठोर सुपरसेट नहीं है, फिर भी लोग दोनों के बीच उच्च स्तर की संगतता की उम्मीद करते हैं।

मोटे तौर पर, एक पीओडी प्रकार एक प्रकार है जो सी के साथ संगत है और शायद समान रूप से महत्वपूर्ण रूप से कुछ एबीआई अनुकूलन के साथ संगत है।

सी के साथ संगत होने के लिए, हमें दो बाधाओं को संतुष्ट करने की आवश्यकता है।

  1. लेआउट इसी सी प्रकार के समान होना चाहिए।
  2. प्रकार को इसी C प्रकार के अनुसार पास किया जाना चाहिए और फ़ंक्शंस से लौटाया जाना चाहिए।

कुछ C ++ विशेषताएँ इसके साथ असंगत हैं।

वर्चुअल मेथड्स में कंपाइलर को एक या एक से अधिक पॉइंट्स को वर्चुअल मेथड टेबल में डालने की आवश्यकता होती है, कुछ ऐसा जो C में मौजूद नहीं है।

उपयोगकर्ता द्वारा परिभाषित कॉपी कंस्ट्रक्टर, मूव कंस्ट्रक्टर, कॉपी असाइनमेंट और डिस्ट्रक्टर्स पैरामीटर गुजरने और लौटने के लिए निहितार्थ हैं। कई सी एबीआई रजिस्टर में छोटे मापदंडों को पारित करते हैं और वापस लौटते हैं, लेकिन उपयोगकर्ता परिभाषित कंस्ट्रक्टर / एसिगमेंट / डिस्ट्रक्टर को दिए गए संदर्भ केवल मेमोरी स्थानों के साथ काम कर सकते हैं।

इसलिए यह परिभाषित करने की आवश्यकता है कि किस प्रकार से "सी संगत" होने की उम्मीद की जा सकती है और कौन से प्रकार नहीं हो सकते हैं। C ++ 03 इस संबंध में कुछ हद तक सख्त था, कोई भी उपयोगकर्ता-परिभाषित कंस्ट्रक्टर अंतर्निहित बिल्डरों को अक्षम कर देगा और उन्हें वापस जोड़ने के किसी भी प्रयास का परिणाम उन्हें उपयोगकर्ता-परिभाषित और इसलिए प्रकार गैर-पॉड होने पर होगा। सी ++ 11 ने चीजों को काफी हद तक खोल दिया, उपयोगकर्ता को अंतर्निहित बिल्डरों को फिर से पेश करने की अनुमति देता है।


8

static_assertC ++ 11 से C ++ 17 और POD प्रभावों के साथ सभी गैर-पीओडी मामलों के उदाहरण

std::is_pod C ++ 11 में जोड़ा गया था, तो आइए अब उस मानक पर विचार करें।

std::is_podhttps://stackoverflow.com/a/48435532/895245 पर उल्लिखित C ++ 20 से हटा दिया जाएगा , आइए इसे अपडेट करें क्योंकि प्रतिस्थापन के लिए समर्थन आता है।

POD प्रतिबंध मानक विकसित होते ही अधिक से अधिक आराम से हो गए हैं, मेरा उद्देश्य ifdefs के माध्यम से उदाहरण में सभी आराम को कवर करना है।

libstdc ++ का परीक्षण थोड़ा कम है: https://github.com/gcc-mirror/gcc/blob/gcc-8_2_0-release/libstdc%2B%2B-v3-testsuite/20_util/is_pod/value.cc लेकिन यह बहुत कम। अनुरक्षक: यदि आप इस पोस्ट को पढ़ते हैं तो कृपया इसे मर्ज करें। मैं सभी C ++ टेस्टसुइट परियोजनाओं का उल्लेख करने के लिए आलसी हूं: /software/199708/is-there-a-compliance-test-for-c-compilers

#include <type_traits>
#include <array>
#include <vector>

int main() {
#if __cplusplus >= 201103L
    // # Not POD
    //
    // Non-POD examples. Let's just walk all non-recursive non-POD branches of cppreference.
    {
        // Non-trivial implies non-POD.
        // https://en.cppreference.com/w/cpp/named_req/TrivialType
        {
            // Has one or more default constructors, all of which are either
            // trivial or deleted, and at least one of which is not deleted.
            {
                // Not trivial because we removed the default constructor
                // by using our own custom non-default constructor.
                {
                    struct C {
                        C(int) {}
                    };
                    static_assert(std::is_trivially_copyable<C>(), "");
                    static_assert(!std::is_trivial<C>(), "");
                    static_assert(!std::is_pod<C>(), "");
                }

                // No, this is not a default trivial constructor either:
                // https://en.cppreference.com/w/cpp/language/default_constructor
                //
                // The constructor is not user-provided (i.e., is implicitly-defined or
                // defaulted on its first declaration)
                {
                    struct C {
                        C() {}
                    };
                    static_assert(std::is_trivially_copyable<C>(), "");
                    static_assert(!std::is_trivial<C>(), "");
                    static_assert(!std::is_pod<C>(), "");
                }
            }

            // Not trivial because not trivially copyable.
            {
                struct C {
                    C(C&) {}
                };
                static_assert(!std::is_trivially_copyable<C>(), "");
                static_assert(!std::is_trivial<C>(), "");
                static_assert(!std::is_pod<C>(), "");
            }
        }

        // Non-standard layout implies non-POD.
        // https://en.cppreference.com/w/cpp/named_req/StandardLayoutType
        {
            // Non static members with different access control.
            {
                // i is public and j is private.
                {
                    struct C {
                        public:
                            int i;
                        private:
                            int j;
                    };
                    static_assert(!std::is_standard_layout<C>(), "");
                    static_assert(!std::is_pod<C>(), "");
                }

                // These have the same access control.
                {
                    struct C {
                        private:
                            int i;
                            int j;
                    };
                    static_assert(std::is_standard_layout<C>(), "");
                    static_assert(std::is_pod<C>(), "");

                    struct D {
                        public:
                            int i;
                            int j;
                    };
                    static_assert(std::is_standard_layout<D>(), "");
                    static_assert(std::is_pod<D>(), "");
                }
            }

            // Virtual function.
            {
                struct C {
                    virtual void f() = 0;
                };
                static_assert(!std::is_standard_layout<C>(), "");
                static_assert(!std::is_pod<C>(), "");
            }

            // Non-static member that is reference.
            {
                struct C {
                    int &i;
                };
                static_assert(!std::is_standard_layout<C>(), "");
                static_assert(!std::is_pod<C>(), "");
            }

            // Neither:
            //
            // - has no base classes with non-static data members, or
            // - has no non-static data members in the most derived class
            //   and at most one base class with non-static data members
            {
                // Non POD because has two base classes with non-static data members.
                {
                    struct Base1 {
                        int i;
                    };
                    struct Base2 {
                        int j;
                    };
                    struct C : Base1, Base2 {};
                    static_assert(!std::is_standard_layout<C>(), "");
                    static_assert(!std::is_pod<C>(), "");
                }

                // POD: has just one base class with non-static member.
                {
                    struct Base1 {
                        int i;
                    };
                    struct C : Base1 {};
                    static_assert(std::is_standard_layout<C>(), "");
                    static_assert(std::is_pod<C>(), "");
                }

                // Just one base class with non-static member: Base1, Base2 has none.
                {
                    struct Base1 {
                        int i;
                    };
                    struct Base2 {};
                    struct C : Base1, Base2 {};
                    static_assert(std::is_standard_layout<C>(), "");
                    static_assert(std::is_pod<C>(), "");
                }
            }

            // Base classes of the same type as the first non-static data member.
            // TODO failing on GCC 8.1 -std=c++11, 14 and 17.
            {
                struct C {};
                struct D : C {
                    C c;
                };
                //static_assert(!std::is_standard_layout<C>(), "");
                //static_assert(!std::is_pod<C>(), "");
            };

            // C++14 standard layout new rules, yay!
            {
                // Has two (possibly indirect) base class subobjects of the same type.
                // Here C has two base classes which are indirectly "Base".
                //
                // TODO failing on GCC 8.1 -std=c++11, 14 and 17.
                // even though the example was copy pasted from cppreference.
                {
                    struct Q {};
                    struct S : Q { };
                    struct T : Q { };
                    struct U : S, T { };  // not a standard-layout class: two base class subobjects of type Q
                    //static_assert(!std::is_standard_layout<U>(), "");
                    //static_assert(!std::is_pod<U>(), "");
                }

                // Has all non-static data members and bit-fields declared in the same class
                // (either all in the derived or all in some base).
                {
                    struct Base { int i; };
                    struct Middle : Base {};
                    struct C : Middle { int j; };
                    static_assert(!std::is_standard_layout<C>(), "");
                    static_assert(!std::is_pod<C>(), "");
                }

                // None of the base class subobjects has the same type as
                // for non-union types, as the first non-static data member
                //
                // TODO: similar to the C++11 for which we could not make a proper example,
                // but with recursivity added.

                // TODO come up with an example that is POD in C++14 but not in C++11.
            }
        }
    }

    // # POD
    //
    // POD examples. Everything that does not fall neatly in the non-POD examples.
    {
        // Can't get more POD than this.
        {
            struct C {};
            static_assert(std::is_pod<C>(), "");
            static_assert(std::is_pod<int>(), "");
        }

        // Array of POD is POD.
        {
            struct C {};
            static_assert(std::is_pod<C>(), "");
            static_assert(std::is_pod<C[]>(), "");
        }

        // Private member: became POD in C++11
        // /programming/4762788/can-a-class-with-all-private-members-be-a-pod-class/4762944#4762944
        {
            struct C {
                private:
                    int i;
            };
#if __cplusplus >= 201103L
            static_assert(std::is_pod<C>(), "");
#else
            static_assert(!std::is_pod<C>(), "");
#endif
        }

        // Most standard library containers are not POD because they are not trivial,
        // which can be seen directly from their interface definition in the standard.
        // /programming/27165436/pod-implications-for-a-struct-which-holds-an-standard-library-container
        {
            static_assert(!std::is_pod<std::vector<int>>(), "");
            static_assert(!std::is_trivially_copyable<std::vector<int>>(), "");
            // Some might be though:
            // /programming/3674247/is-stdarrayt-s-guaranteed-to-be-pod-if-t-is-pod
            static_assert(std::is_pod<std::array<int, 1>>(), "");
        }
    }

    // # POD effects
    //
    // Now let's verify what effects does PODness have.
    //
    // Note that this is not easy to do automatically, since many of the
    // failures are undefined behaviour.
    //
    // A good initial list can be found at:
    // /programming/4178175/what-are-aggregates-and-pods-and-how-why-are-they-special/4178176#4178176
    {
        struct Pod {
            uint32_t i;
            uint64_t j;
        };
        static_assert(std::is_pod<Pod>(), "");

        struct NotPod {
            NotPod(uint32_t i, uint64_t j) : i(i), j(j) {}
            uint32_t i;
            uint64_t j;
        };
        static_assert(!std::is_pod<NotPod>(), "");

        // __attribute__((packed)) only works for POD, and is ignored for non-POD, and emits a warning
        // /programming/35152877/ignoring-packed-attribute-because-of-unpacked-non-pod-field/52986680#52986680
        {
            struct C {
                int i;
            };

            struct D : C {
                int j;
            };

            struct E {
                D d;
            } /*__attribute__((packed))*/;

            static_assert(std::is_pod<C>(), "");
            static_assert(!std::is_pod<D>(), "");
            static_assert(!std::is_pod<E>(), "");
        }
    }
#endif
}

गिटहब ऊपर

के साथ परीक्षण किया गया:

for std in 11 14 17; do echo $std; g++-8 -Wall -Werror -Wextra -pedantic -std=c++$std pod.cpp; done

उबंटू 18.04, जीसीसी 8.2.0 पर।


4

POD की अवधारणा और प्रकार के std::is_podगुणन को C ++ 20 में दर्शाया जाएगा। अधिक जानकारी के लिए यह प्रश्न देखें ।


-7

C ++ के साथ, Plain Old Data का मतलब यह नहीं है कि int, char, इत्यादि जैसी चीजें ही इस्तेमाल की जाती हैं। सादा पुराना डेटा वास्तव में अभ्यास का मतलब है कि आप एक संरचना को स्मृति में एक स्थान से दूसरे स्थान पर ले जा सकते हैं और चीजें ठीक उसी तरह काम करेंगी जैसे आप उम्मीद करेंगे (यानी उड़ा नहीं)। यह तब टूटता है जब आपकी कक्षा, या आपकी कक्षा में कोई भी वर्ग होता है, एक सदस्य के रूप में होता है जो एक सूचक या एक संदर्भ या एक वर्ग होता है जिसमें एक आभासी कार्य होता है। अनिवार्य रूप से, अगर पॉइंटर्स को कहीं और शामिल होना है, तो प्लेन ओल्ड डेटा नहीं।


6
POD स्ट्रक्चर्स में पॉइंटर्स की अनुमति है। संदर्भ नहीं हैं।
j_random_hacker

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