মাপের ইনট কেন ভুল, যখন মাপের (ইন্ট) সঠিক?


97

আমরা জানি যে sizeofকোনও অপারেটর যেকোন ডেটাটাইপ এবং এক্সপ্রেশনের আকার গণনা করার জন্য ব্যবহৃত হয় এবং যখন অপারেন্ডটি একটি এক্সপ্রেশন হয় তখন বন্ধনীগুলি বাদ দেওয়া যায়।

int main()
{
        int a;

        sizeof int;
        sizeof( int );
        sizeof a;
        sizeof( a );

        return 0;
}

এর প্রথম ব্যবহারটি sizeofভুল, অন্যরা সঠিক।

এটি জিসিসি ব্যবহার করে সংকলিত হলে, নিম্নলিখিত ত্রুটি বার্তাটি দেওয়া হবে:

main.c:5:9: error: expected expression beforeint

আমার প্রশ্ন হ'ল সি স্ট্যান্ডার্ড কেন এই ধরণের অপারেশন করতে দেয় না। sizeof intকোনও অস্পষ্টতা সৃষ্টি করবে ?


4
মজার বিষয় হ'ল বন্ধনী ছাড়াই সমস্ত অভিব্যক্তি গ্রহণ করা হয় না: চেষ্টা করুন sizeof (int)a
ফ্রেড ফু

4
@ মিক্কেলকে: ওপি স্ট্যান্ডার্ডিজ কোটগুলির পিছনে যুক্তি জিজ্ঞাসা করছে তিনি ইতিমধ্যে চিহ্নিত উত্তরগুলিতে উল্লেখ করা উক্তিগুলি জানেন।
অলোক

4
@ লন্ডিন: আসলে সংকলন sizeof +(int)aকরার সুবিধা রয়েছে *&;-)
স্টিভ

4
@ স্টেভ জেসোপ আহ ঠিক আছে, এটি কোনও মূল্য নয়। এটি এম্বারকাডেরো সি ++ তে সংকলন করলেও অদ্ভুতভাবে যথেষ্ট। যাইহোক, আমি বিশ্বাস করি আমরা এখনই আনরিয়ার + অপারেটরের জন্য একটি ব্যবহার খুঁজে পেয়েছি! সি প্রোগ্রামিংয়ের ইতিহাসে এটি অবশ্যই প্রথমবারের মতো :)
লন্ডিন

4
@ লন্ডিন: আপনাকে এখনও আনার সাথে সতর্ক থাকতে হবে +। উদাহরণস্বরূপ, sizeof +(char)a == sizeof(int)পূর্ণসংখ্যার প্রচারের কারণে, আপনি যে আকারটির আকার নেওয়ার চেষ্টা করছেন তার সম্পর্কে যদি কোনও উদ্বেগ থাকে তবে কেবল প্যারেন্টেসিসে রাখলে কম ত্রুটি-ঝুঁকির সম্ভাবনা থাকে। সুতরাং আমি নিশ্চিত নই যে আমি এটিকে "ব্যবহার" হিসাবে চিহ্নিত করতে পেরেছি, যদিও আমি স্বীকার করেছি যে আমি এটি ব্যবহার করেছি ...
স্টিভ জেসপ

উত্তর:


101

নিম্নলিখিতটি অস্পষ্ট হতে পারে:

sizeof int * + 1

তাও (sizeof (int*)) + 1নাকি (sizeof(int)) * (+1)?

স্পষ্টতই সি ভাষা অস্পষ্টতা সমাধানের জন্য একটি বিধি চালু করতে পারত, তবে আমি ভাবতে পারি কেন এটি বিরক্ত করেনি। ভাষার যেমন দাঁড়িয়ে আছে তেমন কোনও টাইপ স্পেসিফায়ার কখনই কোনও অভিব্যক্তিতে "নগ্ন" দেখা যায় না এবং সুতরাং দ্বিতীয়টি *টাইপের অংশ বা পাটিগণিত অপারেটর কিনা তা সমাধান করার জন্য নিয়মের কোনও প্রয়োজন নেই ।

বিদ্যমান ব্যাকরণ ইতিমধ্যে এর সম্ভাব্য অস্পষ্টতাকে সমাধান করে sizeof (int *) + 1। এটা (sizeof(int*))+1, না sizeof((int*)(+1))

ফাংশন-স্টাইলের castালাই সিনট্যাক্স সহ সমাধানের জন্য সি ++ এর কিছুটা একই সমস্যা রয়েছে। আপনি লিখতে পারেন int(0)এবং আপনি লিখতে পারেন typedef int *intptr; intptr(0);, তবে আপনি লিখতে পারবেন না int*(0)। সেক্ষেত্রে রেজোলিউশনটি হ'ল "নগ্ন" টাইপটি একটি সরল টাইপের নাম হতে হবে, এটি কোনও পুরানো টাইপ আইডি হতে পারে না যার মধ্যে স্পেস থাকতে পারে বা বিরামচিহ্ন অনুসরণ করতে পারে। সম্ভবত sizeofএকই বাধা দিয়ে সংজ্ঞায়িত করা যেতে পারে , আমি নিশ্চিত নই।


4
সি ++ এর new int*(X)ক্ষেত্রে দ্ব্যর্থক হবে যদি সি ++ নির্দিষ্ট করে না যে নতুন অপারেটর দীর্ঘতম স্ট্রিং নেয় যা সম্ভবত কোনও ধরণের হতে পারে। সুতরাং সি ++ এ তারা আকারের সাথে একই তৈরি করতে পারত, আমার ধারণা। তবে সি ++ এ আপনি বলতে পারেন sizeof int()যা তখন অস্পষ্ট হত (টাইপ বা মান প্রারম্ভিক??)।
জোহানেস স্কাউব -

@ জোহানেস শ্যাব-লিটব: মিম, সুতরাং সম্ভবত তখন সি ++ বলতে পারত যে পার্স করা সম্ভব হলে টাইপটিকেই অগ্রাধিকার দেওয়া হয়, অন্যথায় এটি একটি অভিব্যক্তি। অস্পষ্টতা সমাধান করা হলেও sizeof int()মন্দ গঠন করা হবে ( "কোন operator()জন্য size_t"), যা আমি অনভিপ্রেত হবে আশা!
স্টিভ জেসপ

32

সি 99 স্ট্যান্ডার্ড থেকে

6.5.3.4.2 অপারেটর তার প্রতীক এর আকার (বাইটে), যা একটি অভিব্যক্তি বা ধরনের আলাদা নাম হতে পারে উৎপাদ।
sizeof

আপনার ক্ষেত্রে intনা হয় অভিব্যক্তি বা প্রথম বন্ধনের নাম।


10
আমি কেন বুঝতে পারি না কেন এটি 7 টি আপগেট করে। তিনটি মুছে ফেলা উত্তরের মতো এটি নিয়ম কেন বিদ্যমান তা ব্যাখ্যা করার পরিবর্তে নিয়মটি পুনরাবৃত্তি করে।
ফ্রেড ফু

8
@ আলারসমানস, হ্যাঁ, আমি আপনার সাথে একমত যদিও এটি নিয়মের পুনরাবৃত্তি অব্যাহত রেখেছে, তবে কমপক্ষে, এটি অনুমোদনের পাঠের একটি অংশ দেয়।
যিশু ফাং

4
@larmans আমরা যদি C99 এর প্রতিটি সিদ্ধান্তকে ন্যায়সঙ্গত করার চেষ্টা শুরু করি আমরা সারা বছর এখানে থাকব। এই আলোচনাটি গুটিয়ে নেওয়ার জন্য স্ট্যান্ডার্ডটি উদ্ধৃত করা যতটা ভাল উপায়।
পেরি

4
@ পেরি: আপনি যদি এই ধরণের প্রশ্ন পছন্দ না করেন তবে আপনি প্রশ্নটি যুক্তিযুক্ত হিসাবে বন্ধ করতে ভোট দিতে পারেন।
ফ্রেড ফু

4
সি ++ এর অনুশীলনকারী হিসাবে, এমনকি আমি এই উত্তরটি বুঝতে পারি, আপনি যদি ইংরেজী পড়তে এবং বুঝতে পারেন তবে সমস্যাটি কী তা নিশ্চিত।
কেভ

6

সিতে আকারের অপারেটরটি ব্যবহার করার দুটি উপায় রয়েছে বাক্য গঠনটি হ'ল:

C11 6.5.3 Unary operators
...
sizeof unary-expression
sizeof ( type-name )

যখনই আপনি অপরেন্দ্র হিসাবে কোনও প্রকার ব্যবহার করেন, আপনার ভাষাটির বাক্য গঠন বাক্য সংজ্ঞা অনুসারে আপনার প্রথম বন্ধনী থাকতে হবে। আপনি যদি কোনও অভিব্যক্তিতে আকার ব্যবহার করেন তবে আপনার প্রথম বন্ধনী প্রয়োজন নেই।

সি স্ট্যান্ডার্ড এমন একটি উদাহরণ দেয় যেখানে আপনি এটি কোনও অভিব্যক্তিতে ব্যবহার করতে চাইতে পারেন:

sizeof array / sizeof array[0]

তবে ধারাবাহিকতার জন্য এবং অপারেটরের অগ্রাধিকার সম্পর্কিত বাগগুলি এড়াতে আমি ব্যক্তিগতভাবে সর্বদা () পরিস্থিতি বিবেচনা না করে ব্যবহার করার পরামর্শ দেব।


@ জোহানেস শ্যাব-লিটব আমি সম্মত হই যে সি সি স্ট্যান্ডার্ড কমিটি যখন তারা সি 90 মান নির্দিষ্ট করেছে তখন কীভাবে সি স্ট্যান্ডার্ড কমিটি যুক্তি দিয়েছিল তার কোনও যৌক্তিকতা সরবরাহ করে না। আপনাকে তাদের জিজ্ঞাসা করতে হবে ... এটি কোনও যৌক্তিক সরবরাহ ছাড়াই জবাব দেয়, তবে সি ..৫.৩.৩ তে উল্লিখিত সিনট্যাক্সের যেহেতু সিটেক্সটি এটিকে অনুমতি দেয় না। ওপি এছাড়াও মধ্যে পার্থক্য অবিদিত করলো sizeof expressionএবং sizeof(type), যা এই উত্তরে ব্যাখ্যা করা হয়।
লন্ডিন

(রেকর্ডের জন্য, আমি কেবল C90 এবং C11 উভয় যুক্তিই পড়েছি এবং উভয়ই কোনও ব্যাখ্যা দেয় না।)
লন্ডিন

আমার সন্দেহ হয় এটির জন্য কোনও প্রয়োজনীয় যুক্তি নেই, আসল সি ডিজাইনাররা এটি করার সিদ্ধান্ত নিয়েছে। সম্ভবত এটি প্রাথমিক পার্সারের পক্ষে বিষয়গুলি সহজ করে তুলেছিল। আমি টাইপডেফ এবং ভেরিয়েবল একই নামস্থান ভাগ করে নেওয়ার বিষয়ে একটি উত্তর পোস্ট করতে যাচ্ছিলাম তবে এটি প্রথম সিনট্যাক্সকে অনুমতি দেয় না; এটিকে কেবল পার্সিং বিধিগুলির জন্য প্রয়োজন যে এটি প্যারেন্স না থাকাকালীন চলকটিকে পছন্দ করে, যখন উপস্থিত থাকে তখন প্রকারটি পছন্দ করে এবং নামটি দ্ব্যর্থহীন হলে কোনও ফর্ম ব্যবহার করা যেতে পারে। যেহেতু এটি পরিবর্তন করার দরকার নেই, তাই মান কমিটিগুলি এটিকে একা ফেলেছিল।
বার্মার
আমাদের সাইট ব্যবহার করে, আপনি স্বীকার করেছেন যে আপনি আমাদের কুকি নীতি এবং গোপনীয়তা নীতিটি পড়েছেন এবং বুঝতে পেরেছেন ।
Licensed under cc by-sa 3.0 with attribution required.