আমি malloc ফলাফল ঢালাই না?




casting (18)

এই প্রশ্নের মধ্যে , কেউ comment যে আমি malloc এর ফলাফল নিক্ষেপ করা উচিত নয় , অর্থাত্

int *sieve = malloc(sizeof(int) * length);

বরং:

int *sieve = (int *) malloc(sizeof(int) * length);

কেন এই ক্ষেত্রে হবে?


না, আপনি ফলাফল নিক্ষেপ করবেন না malloc()

সাধারণত, আপনি বা থেকে নিক্ষেপ করা হয় নাvoid *

এটি করার জন্য প্রদত্ত একটি সাধারণ কারণ #include <stdlib.h>অদৃশ্য যেতে পারে যে ব্যর্থতা । এটি এখন দীর্ঘদিনের জন্য কোনও সমস্যা নয় কারণ সি 99 টি নিখরচায় ফাংশন ঘোষণাগুলি অবৈধ করেছে, তাই যদি আপনার কম্পাইলার কমপক্ষে C99 এর সাথে সামঞ্জস্যপূর্ণ হয় তবে আপনাকে ডায়াগনস্টিক বার্তা পাবেন।

কিন্তু অযৌক্তিক পয়েন্টার কাস্টগুলি পরিচয় করানোর জন্য অনেক শক্তিশালী কারণ নেই:

সি, একটি পয়েন্টার কাস্ট প্রায় সবসময় একটি ত্রুটি । নিম্নলিখিত নিয়মটি ( N1570 §6.5 p7, সি 11 এর সর্বশেষ খসড়া) কারণে:

একটি বস্তু এর সংরক্ষিত মান শুধুমাত্র একটি lvalue অভিব্যক্তি নিম্নলিখিত প্রকারের অন্যতম যে অ্যাক্সেস করেছে হইবে:
- একটি টাইপ বস্তুর কার্যকর ধরনের সঙ্গে সামঞ্জস্যপূর্ণ,
- একটি টাইপ বস্তু, কার্যকর ধরনের সঙ্গে সামঞ্জস্যপূর্ণ একটি যোগ্যতাসম্পন্ন সংস্করণ
- বস্তুর কার্যকর প্রকারের সাথে
স্বাক্ষরিত বা অচেনা টাইপ যা একটি প্রকার , - কার্যকর একটি ধরনের কার্যকর সংস্করণের সাথে সম্পর্কিত স্বাক্ষরিত বা স্বাক্ষরিত প্রকারের একটি টাইপ
- একটি সমষ্টিগত বা ইউনিয়ন টাইপ যা একটি তার সদস্যদের মধ্যে (উদাহরণস্বরূপ, একটি সর্বজনীন বা অন্তর্গত ইউনিয়নের সদস্য), বা
- একটি চরিত্র টাইপ মধ্যে উল্লিখিত ধরনের ।

এই কঠোর আলাইজিং নিয়ম হিসাবে পরিচিত হয় । তাই নিম্নলিখিত কোডটি অনির্ধারিত আচরণ :

long x = 5;
double *p = (double *)&x;
double y = *p;

এবং, কখনও কখনও বিস্ময়করভাবে, নিম্নলিখিতটিও নিম্নরূপ:

struct foo { int x; };
struct bar { int x; int y; };
struct bar b = { 1, 2};
struct foo *p = (struct foo *)&b;
int z = p->x;

কখনও কখনও, আপনি কি পয়েন্টার কাস্ট করার জন্য প্রয়োজন, কিন্তু দেওয়া কঠোর এলিয়াসিং নিয়ম , আপনি এটি সঙ্গে খুব সতর্কতা অবলম্বন করা আবশ্যক আছে। সুতরাং, আপনার কোডটিতে কোনও পয়েন্টার ঢোকানো একটি স্থান যেখানে এটির বৈধতার জন্য আপনার দুবার চেক করতে হবে । অতএব, আপনি একটি অপ্রয়োজনীয় পয়েন্টার কাস্ট লিখতে না।

TL; ড

সংক্ষেপে: কারণ C তে, কোনও পয়েন্টার কাস্টের কোনও ঘটনাকে বিশেষ মনোযোগ দেওয়ার জন্য কোডের জন্য লাল পতাকা জাগানো উচিত, আপনাকে কখনই অপ্রয়োজনীয় পয়েন্টার কাস্টগুলি লিখতে হবে না ।

সাইড নোট:

  • আছে ক্ষেত্রে যেখানে আপনি আসলে প্রয়োজন একটি ঢালাই void *, যেমন আপনি একটি পয়েন্টার মুদ্রণ করতে চান:

    int x = 5;
    printf("%p\n", (void *)&x);
    

    কাস্ট এখানে প্রয়োজনীয়, কারণ printf()একটি ভেরিয়েডিক ফাংশন, তাই অন্তর্নিহিত রূপান্তর কাজ করে না।

  • সি ++, পরিস্থিতি ভিন্ন। উদ্ভাবিত ক্লাস বস্তুর সঙ্গে ডিল করার সময় পয়েন্টার ধরনের ঢালাই কিছুটা সাধারণ (এবং সঠিক)। অতএব, এটা জ্ঞান করে তোলে যে সি ++ এ, এবং থেকে রূপান্তর void *হয় না অন্তর্নিহিত। সি ++ কাস্টিং বিভিন্ন স্বাদ একটি সম্পূর্ণ সেট আছে।


  1. অন্যান্য বিবৃত হিসাবে, এটি সি জন্য প্রয়োজন হয় না, কিন্তু সি ++ জন্য।

  2. কাস্ট সহ একটি সি প্রোগ্রাম বা ফাংশন C ++ হিসাবে কম্পাইল করার অনুমতি দিতে পারে।

  3. C তে এটি অপ্রয়োজনীয়, অকার্যকর * স্বয়ংক্রিয়ভাবে এবং নিরাপদে অন্য কোন পয়েন্টার প্রকারে প্রচার করা হয়।

  4. কিন্তু আপনি যদি তা নিক্ষেপ করেন তবে আপনি stdlib.h অন্তর্ভুক্ত করতে ভুলে গেলে এটি একটি ত্রুটি লুকিয়ে রাখতে পারে । এটি ক্র্যাশগুলি (বা, খারাপ, কোডের কিছু পুরোপুরি ভিন্ন অংশে পরে পর্যন্ত ক্র্যাশ সৃষ্টি করে না) সৃষ্টি করতে পারে।

    কারণ mdoc জন্য prototype stdlib.h পাওয়া যায়। মল্লোকের জন্য প্রোটোটাইপের অনুপস্থিতিতে, স্ট্যান্ডার্ডটি প্রয়োজন যে সি কম্পাইলারটি ম্যালোককে কোনও int প্রদান করে। যদি কোন কাস্ট না থাকে তবে এই পূর্ণসংখ্যা পয়েন্টারকে বরাদ্দ করা হলে একটি সতর্কতা জারি করা হয়; যাইহোক, নিক্ষেপ সঙ্গে, এই সতর্কতা উত্পাদিত হয় না, একটি বাগ গোপন।


GCC এবং Clang ব্যবহৃত মানুষ নষ্ট হয়। এটা সব ভাল যে নেই।

আমি ব্যবহার করা প্রয়োজন হয়েছে staggeringly বয়সী কম্পাইলার দ্বারা বছর ধরে চমত্কার ভয়ঙ্কর হয়েছে। প্রায়শই কোম্পানি এবং পরিচালকরা পরিবর্তনশীল কম্পাইলারগুলির জন্য অতিমাত্রায় রক্ষণশীল পদ্ধতি গ্রহণ করে এবং কোনও নতুন কম্পাইলার (উন্নত মানের সম্মতি এবং কোড অপ্টিমাইজেশান সহ) তাদের সিস্টেমে কাজ করবে কিনা তাও পরীক্ষা করবে না। কাজের ডেভেলপারদের জন্য বাস্তব বাস্তবতা হল যে যখন আপনি কোডিং করছেন তখন আপনাকে আপনার ঘাঁটিগুলি ঢেকে রাখতে হবে এবং দুর্ভাগ্যক্রমে, আপনার কোডটিতে কোন কম্পাইলারটি প্রয়োগ করা যেতে পারে তা নিয়ন্ত্রণ করতে না পারলেও ম্যালওক্সগুলি কাস্টিং একটি ভাল অভ্যাস।

আমি আরো পরামর্শ দিচ্ছি যে অনেক সংস্থা তাদের নিজস্ব কোডিং মান প্রয়োগ করে এবং এটি যদি এটি সংজ্ঞায়িত করা হয় তবে এটি এমন পদ্ধতি হওয়া উচিত। সুস্পষ্ট নির্দেশনার অনুপস্থিতিতে আমি আদর্শের নিষ্ঠুর সঙ্গতির পরিবর্তে সর্বত্র সংকলন করার জন্য সর্বাধিক সম্ভবত যেতে চাই।

বর্তমান মান অনুযায়ী এটি প্রয়োজনীয় নয় এমন যুক্তিটি বেশ বৈধ। কিন্তু সেই যুক্তি বাস্তব বিশ্বের বাস্তবতাকে বাদ দেয়। আমরা দিনের মান অনুযায়ী একচেটিয়াভাবে শাসিত একটি বিশ্বের কোড না, কিন্তু আমি "স্থানীয় ব্যবস্থাপনা এর বাস্তবতা ক্ষেত্র" কল করতে চান কি বাস্তবতা দ্বারা। এবং যে স্পন্দিত সময়ের চেয়ে আরো নিচু এবং twisted ছিল। :-)

YMMV।

আমি একটি defensive অপারেশন হিসাবে malloc কাস্টিং মনে ঝোঁক। সুন্দর না, নিখুঁত না, কিন্তু সাধারণত নিরাপদ। (আন্তরিকভাবে, আপনি stdlib.h অন্তর্ভুক্ত না করে থাকেন তাহলে আপনি malloc ঢালাই চেয়ে আরো সমস্যা উপায় আছে !)।


অন্যান্য বিবৃত হিসাবে, এটি সি জন্য প্রয়োজন হয় না, কিন্তু সি ++ জন্য। আপনি যদি মনে করেন যে আপনি সি ++ কম্পাইলারের সাথে আপনার সি কোডটি কম্পাইল করতে যাচ্ছেন, কোন কারনে এটির পরিবর্তে আপনি একটি ম্যাক্রো ব্যবহার করতে পারেন, যেমন:

#ifdef __cplusplus
# define NEW(type, count) ((type *)calloc(count, sizeof(type)))
#else
# define NEW(type, count) (calloc(count, sizeof(type)))
#endif

এই ভাবে আপনি এখনও এটি খুব কমপক্ষে লিখতে পারেন:

int *sieve = NEW(int, 1);

এবং এটি সি এবং সি ++ জন্য কম্পাইল হবে।


আপনি নিক্ষেপ করবেন, কারণ:

  • এটি আপনার কোডটি সি এবং সি ++ এর মধ্যে আরও পোর্টেবল করে এবং SO SO অভিজ্ঞতা দেখায়, অনেকগুলি প্রোগ্রামার দাবি করে যে তারা সি-তে লেখা হয় যখন তারা সত্যিই C ++ (বা সি প্লাস স্থানীয় কম্পাইলার এক্সটেনশনগুলিতে) লেখা হয়।
  • এটি করতে ব্যর্থ হলে ত্রুটিটি লুকিয়ে থাকতে পারে : type * বনাম type ** লিখতে বিভ্রান্তিকর সমস্ত উদাহরণ উদাহরণ type ** নোট করুন।
  • ধারণাটি যে এটি আপনাকে লক্ষ্য করে রাখে সেটি #include উপযুক্ত শিরোনাম ফাইল #include করতে ব্যর্থ হয়েছে যাতে গাছগুলির জন্য বনটি মিস করে । এটি এমনই বলে যে "কম্পাইলারকে প্রোটোটাইপগুলি দেখতে না দেওয়ার অভিযোগে আপনি অভিযোগ করতে ব্যর্থ হয়েছেন সে বিষয়ে চিন্তা করবেন না - যে প্যাস্কি stdlib.h মনে রাখা প্রকৃত সত্য!"
  • এটি একটি অতিরিক্ত জ্ঞানীয় ক্রস চেক শক্তি । এটি আপনি যে পরিবর্তনশীল কাঁচামাল জন্য করছেন করছেন গাণিতিক পাশে ডান (অভিযুক্ত) পছন্দসই টাইপ রাখে। আমি bet আপনি একটি SO স্টাডি করতে পারেন যা দেখায় যে malloc() কাস্ট যখন কাস্ট থাকে তখন আরো দ্রুত ধরা হয়। অঙ্গীকার হিসাবে, উদ্দেশ্য হ্রাস বাগ হ্রাস যে উদ্ঘাটন।
  • মেশিন চেক করতে পারেন যে একটি উপায় নিজেকে পুনরাবৃত্তি প্রায়ই একটি দুর্দান্ত ধারণা। আসলে, এটি একটি দাবি যা, এবং কাস্ট এই ব্যবহার একটি দাবি। সংশোধনগুলি এখনও কোডটি সঠিক করার জন্য আমাদের কাছে সবচেয়ে সাধারণ কৌশল, কারণ টুরিং এত বছর আগে ধারণাটি নিয়ে এসেছিল।

আমি টাইপ সিস্টেমে কুৎসিত গর্তের অপব্যবহার দেখানোর জন্য কেবল ঢালাই করি, যা নিম্নোক্ত স্নিপেটের মতো কোডগুলিকে ডায়াগনস্টিক্স ছাড়াই কম্পাইল করার অনুমতি দেয়, যদিও খারাপ রূপান্তর নিয়ে কোনও কাস্ট ব্যবহার করা হয় না:

double d;
void *p = &d;
int *q = p;

আমি যে বিদ্যমান ছিল না (এবং এটা সি ++ না) এবং তাই আমি নিক্ষেপ। এটা আমার স্বাদ, এবং আমার প্রোগ্রামিং রাজনীতি প্রতিনিধিত্ব করে। আমি শুধু একটি পয়েন্টার ভোটদান করছি না, কিন্তু কার্যকরভাবে, একটি ব্যালট ভোটদান , এবং নির্বোধ demons দান আউট ।যদি আমি আসলে নির্বোধতা নিক্ষেপ করতে পারি না , তাহলে অন্তত আমাকে প্রতিবাদের অঙ্গভঙ্গি দিয়ে তা করার ইচ্ছা প্রকাশ করুক।

প্রকৃতপক্ষে, একটি ভাল অভ্যাস mallocফিরতি ফাংশন (এবং বন্ধুদের) কে ফিরানো unsigned char *এবং মূলত void *আপনার কোডটিতে কখনই ব্যবহার করা হয় না । যদি আপনার জেনেরিক পয়েন্টার-টু-ই-অবজেক্টের প্রয়োজন হয়, তবে একটি char *বা ব্যবহার করুন unsigned char *এবং উভয় দিকের মধ্যে থাকে। এক ঝলক যে indulged হতে পারে, সম্ভবত, যেমন memsetএবং memcpyবিনাশ ছাড়া ফাংশন ব্যবহার করা হয় ।

ঢালাই এবং সি ++ সামঞ্জস্য বিষয় অন, যাতে এটি প্রনয়ন উভয় সি এবং সি ++ (যে ক্ষেত্রে আপনি যদি আপনার কোড লিখতে হবে ফেরত মান নিক্ষেপ mallocযখন এটি ব্যতীত অন্য কিছু বরাদ্দ void *), আপনি একটি খুব সহায়ক কি করতে পারেন নিজের জন্য জিনিস: আপনি সি ++ শৈলীতে অনুবাদ করতে কাস্ট করার জন্য ম্যাক্রোগুলি ব্যবহার করতে পারেন যা C ++ হিসাবে কম্পাইল করে, কিন্তু C হিসাবে কম্পাইল করার সময় একটি সি কাস্টে কমাতে পারেন:

/* In a header somewhere */
#ifdef __cplusplus
#define strip_qual(TYPE, EXPR) (const_cast<TYPE>(EXPR))
#define convert(TYPE, EXPR) (static_cast<TYPE>(EXPR))
#define coerce(TYPE, EXPR) (reinterpret_cast<TYPE>(EXPR))
#else
#define strip_qual(TYPE, EXPR) ((TYPE) (EXPR))
#define convert(TYPE, EXPR) ((TYPE) (EXPR))
#define coerce(TYPE, EXPR) ((TYPE) (EXPR))
#endif

আপনি যদি এই ম্যাক্রোগুলি অনুসরণ করেন, তবে grepএই সনাক্তকারীর জন্য আপনার কোড বেসের সহজ অনুসন্ধান আপনাকে দেখাবে যেখানে আপনার সমস্ত কাস্টগুলি রয়েছে, যাতে আপনি তাদের মধ্যে কোনটি ভুল কিনা তা পর্যালোচনা করতে পারেন।

তারপরে, এগিয়ে যান, যদি আপনি নিয়মিত কোডটি সি ++ সহ সংকলন করেন তবে এটি একটি উপযুক্ত কাস্টের ব্যবহারকে কার্যকর করবে। উদাহরণস্বরূপ, যদি আপনি strip_qualকেবল একটি constবা অপসারণের জন্য ব্যবহার করেন volatileতবে প্রোগ্রামটি এমনভাবে পরিবর্তিত হয় যে কোন ধরনের রূপান্তর এখন জড়িত, আপনি একটি ডায়াগনস্টিক পাবেন এবং আপনি পছন্দসই রূপান্তর পেতে কাস্টগুলির সমন্বয় ব্যবহার করতে হবে।

এই ম্যাক্রোগুলি মেনে চলতে আপনাকে সাহায্য করার জন্য, GNU C ++ (সি নয়!) কম্পাইলারের একটি সুন্দর বৈশিষ্ট্য রয়েছে: একটি শৈলী কাস্টগুলির সমস্ত ঘটনার জন্য একটি ঐচ্ছিক ডায়গনিস্টিক তৈরি করা হয়।

     -Wold-style-cast (C++ and Objective-C++ only)
         Warn if an old-style (C-style) cast to a non-void type is used
         within a C++ program.  The new-style casts (dynamic_cast,
         static_cast, reinterpret_cast, and const_cast) are less vulnerable
         to unintended effects and much easier to search for.

যদি আপনার সি কোড সি ++ হিসাবে সংকলন করে তবে আপনি এই -Wold-style-castবিকল্পটি ব্যবহার করতে পারেন (type)কাস্টিং সিনট্যাক্সের সমস্ত ঘটনা খুঁজে বের করতে যা কোডটিতে সরাতে পারে এবং উপরের ম্যাক্রোগুলির মধ্যে থেকে একটি উপযুক্ত পছন্দ দ্বারা এটি প্রতিস্থাপন করে এই ডায়গনিস্টিকগুলিতে ফলো করুন। সমন্বয়, প্রয়োজন হলে)।

রূপান্তরগুলির এই চিকিত্সাটি "ক্লিন সি" -এ কাজ করার জন্য একক সর্বাধিক স্বতন্ত্র প্রযুক্তিগত অনুমোদন: মিলিত সি এবং সি ++ উপভাষা, যা টেকনিক্যালি রিটার্ন মান কাস্টিংকে সমর্থন করে malloc


এটা প্রোগ্রামিং ভাষা এবং কম্পাইলার উপর নির্ভর করে। যদি আপনি C তে malloc ব্যবহার করেন তবে এটি কাস্ট করার জন্য কোনও প্রয়োজন নেই, এটি স্বয়ংক্রিয়ভাবে কাস্ট টাইপ করবে, তবে যদি আপনার C ++ ব্যবহার করা হয় তবে আপনাকে কাস্ট টাইপ করা উচিত কারণ malloc একটি void* টাইপ ফেরত দেবে।


প্রত্যাবর্তিত টাইপটি অকার্যকর *, যা ডেফারেন্সযোগ্য হওয়ার জন্য পছন্দসই ধরনের তথ্য পয়েন্টারে ঢোকানো যেতে পারে।


সি তে, আপনি malloc রিটার্ন মান নিক্ষেপ করতে হবে না। Malloc দ্বারা অকার্যকর পয়েন্টার পয়েন্টার স্বয়ংক্রিয়ভাবে সঠিক টাইপ রূপান্তর করা হয়। যাইহোক, যদি আপনি আপনার কোডটি সি ++ কম্পাইলারের সাথে কম্পাইল করতে চান তবে একটি কাস্ট প্রয়োজন। সম্প্রদায়ের মধ্যে একটি পছন্দসই বিকল্প নিম্নলিখিত ব্যবহার করা হয়:

int *sieve = malloc(sizeof *sieve * length);

যা অতিরিক্তভাবে আপনি চেইনের ধরন পরিবর্তন করলে অভিব্যক্তিটির ডান দিকের দিক পরিবর্তন করার বিষয়ে চিন্তা করতে আপনাকে মুক্ত করে।

কাস্টস খারাপ, মানুষ নির্দেশ করেছে। বিশেষভাবে পয়েন্টার casts।


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

#include <stdlib.h>
#define NEW_ARRAY(ptr, n) (ptr) = malloc((n) * sizeof *(ptr))
#define NEW(ptr) NEW_ARRAY((ptr), 1)

এই জায়গায় সঙ্গে আপনি সহজেই বলতে পারেন

NEW_ARRAY(sieve, length);

অ-গতিশীল অ্যারেগুলির জন্য, তৃতীয়টির অবশ্যই ফাংশন ম্যাক্রো থাকতে হবে

#define LEN(arr) (sizeof (arr) / sizeof (arr)[0])

যা অ্যারে loops নিরাপদ এবং আরো সুবিধাজনক করে তোলে:

int i, a[100];

for (i = 0; i < LEN(a); i++) {
   ...
}

জিএনইউ সি লাইব্রেরী রেফারেন্স ম্যানুয়াল এইটি কি বলে:

আপনি কোনও নিক্ষেপ ছাড়াই কোনও পয়েন্টার ভেরিয়েবলের malloc এর ফলাফল সংরক্ষণ করতে পারেন, কারণ ISO সি স্বয়ংক্রিয়ভাবে টাইপ void * অন্য কোনও পয়েন্টারে পরিবর্তিত হয়। কিন্তু নিক্ষেপ অপারেটর ছাড়া অন্য প্রসঙ্গে কাস্টের প্রয়োজন হয় অথবা আপনি যদি আপনার কোডটি ঐতিহ্যগত সিতে চালাতে চান।

এবং প্রকৃতপক্ষে আইএসও সি 11 স্ট্যান্ডার্ড (p347) তাই বলে:

যদি বরাদ্দকরণ সফল হয় তবে পয়েন্টারটি সঠিকভাবে সংলগ্ন হয় যাতে এটি একটি মৌলিক সারিবদ্ধকরণ প্রয়োজনীয়তার সাথে কোনও বস্তুর কোনো পয়েন্টারকে বরাদ্দ করা যেতে পারে এবং তারপরে বরাদ্দকৃত স্থানটিতে এমন বস্তুর অ্যারে বা অ্যারে অ্যাক্সেস করার জন্য ব্যবহৃত হয়। স্থান স্পষ্টভাবে deallocated হয়)


Wikipedia থেকে

কাস্টিং সুবিধা

  • কাস্ট সহ একটি সি প্রোগ্রাম বা ফাংশন C ++ হিসাবে কম্পাইল করার অনুমতি দিতে পারে।

  • কাস্ট মূলত একটি গৃহস্থালি * ফিরে যে malloc প্রাক 1989 এর সংস্করণ জন্য অনুমতি দেয়।

  • কাস্টিং টাইপ আকারে অসঙ্গতি সনাক্ত করতে সহায়তা করতে পারে গন্তব্য পয়েন্টার ধরন পরিবর্তন করা উচিত, বিশেষ করে যদি পয়েন্টারকে malloc () কল থেকে দূরে ঘোষণা করা হয় (যদিও আধুনিক কম্পাইলার এবং স্ট্যাটিক বিশ্লেষক কাস্টের প্রয়োজন ব্যতীত এমন আচরণে সতর্ক থাকতে পারে)।

কাস্টিং অসুবিধা

  • ANSI সি মান অধীনে, কাস্ট অনাদায়ী হয়।

  • কাস্ট যোগ করা শিরোনাম stdlib.h অন্তর্ভুক্ত করতে মাস্ক ব্যর্থতা হতে পারে, যা malloc জন্য প্রোটোটাইপ পাওয়া যায়। মল্লোকের জন্য প্রোটোটাইপের অনুপস্থিতিতে, স্ট্যান্ডার্ডটি প্রয়োজন যে সি কম্পাইলারটি ম্যালোককে কোনও int প্রদান করে। যদি কোন কাস্ট না থাকে তবে এই পূর্ণসংখ্যা পয়েন্টারকে বরাদ্দ করা হলে একটি সতর্কতা জারি করা হয়; যাইহোক, নিক্ষেপ সঙ্গে, এই সতর্কতা উত্পাদিত হয় না, একটি বাগ গোপন। নির্দিষ্ট আর্কিটেকচার এবং ডেটা মডেলগুলিতে (যেমন 64-বিট সিস্টেমে LP64, যেখানে দীর্ঘ এবং পয়েন্টারগুলি 64-বিট এবং int- 32-বিট হয়), এই ত্রুটিটি প্রকৃতপক্ষে অনির্ধারিত আচরণের ফলস্বরূপ হতে পারে, কারণ নিখরচায় ঘোষণা করা ম্যালোক একটি 32- বিট মান যখন আসলে সংজ্ঞায়িত ফাংশন একটি 64 বিট মান প্রদান করে। কলিং কনভেনশন এবং মেমরি বিন্যাসের উপর নির্ভর করে, এটি স্ট্যাক ভাঙা ফলাফল হতে পারে। এই সমস্যাটি আধুনিক কম্পাইলারগুলির মধ্যে কোনও নজরদারি করার সম্ভাবনা কম নয়, কারণ তারা একত্রে সতর্কতা অবলম্বন করে যে সতর্কতা অবলম্বন করা হয়েছে, তাই একটি সতর্কতা এখনও উপস্থিত হবে। উদাহরণস্বরূপ, জিसीसीের ডিফল্ট আচরণ হল একটি সতর্কতা প্রদর্শন করা যা "অন্তর্নির্মিত ফাংশনের অসঙ্গতিপূর্ণ ঘোষণামূলক ঘোষণা" পড়ে থাকে কিনা তা নির্বিশেষে না থাকা সত্ত্বেও না।

  • যদি পয়েন্টারটির ঘোষণাটি তার ঘোষণায় পরিবর্তিত হয়, তবে একজনকেও ম্যালোক বলা এবং কাস্ট করার সমস্ত লাইন পরিবর্তন করতে হবে।

যদিও ঢালাই ছাড়া malloc পছন্দসই পদ্ধতি এবং বেশিরভাগ অভিজ্ঞ প্রোগ্রামার এটি পছন্দ করে , তবে আপনি বিষয়গুলি সম্পর্কে সচেতন থাকা আপনার যে কোনটি ব্যবহার করতে হবে।

অর্থাৎ: যদি সি সি ++ হিসাবে সি সি সংকলন করতে হয় তবে (যদিও এটি আলাদা ভাষা) তবে আপনি কাস্টিংয়ের সাথে malloc ব্যবহার করতে হবে।


malloc ফলাফলগুলি নিক্ষেপ করা বাধ্যতামূলক নয়, কারণ এটি void* , এবং একটি void* কোনো ডেটাপাইপকে নির্দেশ করা যেতে পারে।


Malloc কাস্টিং সি মধ্যে অপ্রয়োজনীয় কিন্তু C ++ মধ্যে বাধ্যতামূলক।

কাস্টিং এর কারণে অপ্রয়োজনীয়:

  • void * স্বয়ংক্রিয়ভাবে এবং নিরাপদে C এর ক্ষেত্রে অন্য কোন পয়েন্টার প্রকারে প্রচার করা হয়।
  • যদি আপনি অন্তর্ভুক্ত করতে ভুলে গেছেন তবে এটি একটি ত্রুটি লুকিয়ে রাখতে পারে <stdlib.h>। এই ক্র্যাশ হতে পারে।
  • পয়েন্টার এবং পূর্ণসংখ্যা আলাদাভাবে আকারে থাকলে, আপনি কাস্টিংয়ের মাধ্যমে একটি সতর্কতা গোপন করছেন এবং আপনার ফিরতি ঠিকানাটির বিট হারাতে পারে।
  • যদি পয়েন্টারটির ঘোষণাটি তার ঘোষণা অনুসারে পরিবর্তিত হয়, তবে mallocএকে বলা এবং কাস্ট করা সমস্ত লাইন পরিবর্তন করতে হবে ।

অন্যদিকে, কাস্টিং আপনার প্রোগ্রামের পোর্টেবিলিটি বাড়িয়ে তুলতে পারে। অর্থাৎ, এটি একটি সি প্রোগ্রাম বা ফাংশনকে সি ++ হিসাবে কম্পাইল করার অনুমতি দেয়।


একটি অকার্যকর পয়েন্টার একটি জেনেরিক পয়েন্টার এবং সি একটি অকার্যকর পয়েন্টার টাইপ থেকে অন্য ধরনের প্রকার রূপান্তর সমর্থন করে, তাই স্পষ্টভাবে টাইপcasting এর কোন প্রয়োজন নেই।

যাইহোক, যদি আপনি একই কোডটি সি ++ প্ল্যাটফর্মের সাথে পুরোপুরি সামঞ্জস্যপূর্ণ কাজ করতে চান, যা অন্তর্নিহিত রূপান্তর সমর্থন করে না তবে আপনাকে টাইপcastিং করতে হবে, তাই এটি সমস্ত ব্যবহারযোগ্যতার উপর নির্ভর করে।


কাস্টিং শুধুমাত্র সি ++ নয়। সি ক্ষেত্রে আপনি একটি সি ++ কম্পাইলার ব্যবহার করছেন তবে আপনি ভালভাবে সি কম্পাইলারে পরিবর্তন করুন।


অকার্যকর পয়েন্টারের পিছনে ধারণাটি হল যে এটি কোনও ডেটা টাইপে ঢোকানো যায় যা ম্যালোককে ফেরত দেয়। এছাড়াও আপনি স্বয়ংক্রিয় টাইপcasting সচেতন হতে হবে। তাই পয়েন্টারটি নিক্ষেপ করা বাধ্যতামূলক নয় তবে আপনাকে অবশ্যই এটি করতে হবে। এটি কোড পরিষ্কার রাখতে সহায়তা করে এবং ডিবাগিংয়ে সহায়তা করে


আমি কাস্ট করতে পছন্দ, কিন্তু নিজে না। আমার প্রিয় গ্লিব থেকে ব্যবহার g_newএবং g_new0ম্যাক্রো হয়। গ্লিব ব্যবহার করা হয় না, আমি অনুরূপ ম্যাক্রো যোগ হবে। যারা ম্যাক্রো টাইপ নিরাপত্তা আপোস ছাড়া কোড অনুলিপি কমাতে। যদি আপনি ভুল টাইপ পান তবে আপনি অ-অকার্যকর পয়েন্টারগুলির মধ্যে একটি নিখুঁত কাস্ট পাবেন, যা একটি সতর্কতা (C ++ এ ত্রুটি) সৃষ্টি করবে। আপনি সংজ্ঞায়িত শিরোনাম অন্তর্ভুক্ত করতে ভুলে যান g_newএবং g_new0, আপনি একটি ত্রুটি পাবেন। g_newএবং g_new0উভয় একই আর্গুমেন্ট নিতে, mallocযে বিপরীতে কম আর্গুমেন্ট লাগে calloc। শুধু 0শূন্য-প্রাথমিক মেমরি পেতে যোগ করুন । কোড পরিবর্তন ছাড়া একটি সি ++ কম্পাইলার সঙ্গে সংকলিত করা যেতে পারে।





casting