সি ++ এর কেন হেডার ফাইল এবং .cpp ফাইল রয়েছে?
সি ++ এর কেন হেডার ফাইল এবং .cpp ফাইল রয়েছে?
উত্তর:
ঠিক আছে, মূল কারণটি হবে বাস্তবায়ন থেকে ইন্টারফেসকে আলাদা করা। শিরোনামটি "কী" একটি শ্রেণি (বা যা বাস্তবায়িত হচ্ছে) কী করবে তা ঘোষণা করে, যখন সিপিপি ফাইলটি "কীভাবে" এই বৈশিষ্ট্যগুলি সম্পাদন করবে তা সংজ্ঞায়িত করে।
এটি নির্ভরতা হ্রাস করে যাতে শিরোনাম ব্যবহার করে এমন কোডগুলি প্রয়োগের সমস্ত বিবরণ এবং কেবল তার জন্য প্রয়োজনীয় অন্য কোনও শ্রেণি / শিরোনামগুলি জেনে রাখে না। এটি সংকলনের সময়গুলি এবং বাস্তবায়নের কোনও কিছু পরিবর্তিত হলে পুনঃসংশোধনের পরিমাণ হ্রাস করবে।
এটি নিখুঁত নয় এবং আপনি সাধারণত পিম্পল ইডিয়ামের মতো কৌশলগুলি যথাযথভাবে পৃথক ইন্টারফেস এবং বাস্তবায়ন করতে পারেন তবে এটি একটি ভাল শুরু।
সি ++ তে একটি সংকলন 2 টি বড় ধাপে করা হয়:
প্রথমটি বাইনারি "অবজেক্ট" ফাইলগুলিতে "উত্স" পাঠ্য ফাইলগুলির সংকলন: সিপিপি ফাইলটি সংকলিত ফাইল এবং অন্য সিপিপি ফাইল (বা এমনকি গ্রন্থাগার) সম্পর্কে কোনও জ্ঞান ছাড়াই সংকলিত হয়, যদি না এটি কাঁচা ঘোষণার মাধ্যমে খাওয়ানো হয় বা শিরোনাম অন্তর্ভুক্তি। সিপিপি ফাইলটি সাধারণত একটি .OBJ বা একটি .O "অবজেক্ট" ফাইলে সংকলিত হয়।
দ্বিতীয়টি হ'ল সমস্ত "অবজেক্ট" ফাইলগুলির সাথে একত্রে লিঙ্ক করা, এবং এইভাবে চূড়ান্ত বাইনারি ফাইল তৈরি করা (হয় একটি লাইব্রেরি বা এক্সিকিউটেবল)।
এইচপিপি এই সমস্ত প্রক্রিয়াতে ফিট করে কোথায়?
প্রতিটি সিপিপি ফাইলের সংকলন অন্যান্য সমস্ত সিপিপি ফাইল থেকে স্বতন্ত্র, যার অর্থ যদি এ.সি.পি.পি. বি.সি.পি.পি. তে সংজ্ঞায়িত একটি চিহ্নের প্রয়োজন হয়, যেমন:
// A.CPP
void doSomething()
{
doSomethingElse(); // Defined in B.CPP
}
// B.CPP
void doSomethingElse()
{
// Etc.
}
এটি সংকলন করবে না কারণ A.CPP এর কাছে "doSomethingElse" উপস্থিত থাকার কোন উপায় নেই ... যদি না এসিপিপিতে কোনও ঘোষণা না থাকে যেমন:
// A.CPP
void doSomethingElse() ; // From B.CPP
void doSomething()
{
doSomethingElse() ; // Defined in B.CPP
}
তারপরে, আপনার যদি সিসিপিপি থাকে যা একই প্রতীক ব্যবহার করে, আপনি তারপরে ঘোষণার অনুলিপি / আটকান ...
হ্যাঁ, একটি সমস্যা আছে। অনুলিপি / আটকানো বিপজ্জনক, এবং বজায় রাখা কঠিন। যার অর্থ হ'ল আমাদের যদি অনুলিপি / পেস্ট না করার কিছু উপায় থাকে এবং এখনও প্রতীকটি ঘোষনা করে তবে এটি দুর্দান্ত হবে ... আমরা কীভাবে এটি করতে পারি? কিছু পাঠ্য ফাইল অন্তর্ভুক্ত করে যা সাধারণত .h, .hxx, .h ++ বা, সি ++ ফাইলগুলির জন্য আমার পছন্দের সাথে সংযুক্ত থাকে, .hpp:
// B.HPP (here, we decided to declare every symbol defined in B.CPP)
void doSomethingElse() ;
// A.CPP
#include "B.HPP"
void doSomething()
{
doSomethingElse() ; // Defined in B.CPP
}
// B.CPP
#include "B.HPP"
void doSomethingElse()
{
// Etc.
}
// C.CPP
#include "B.HPP"
void doSomethingAgain()
{
doSomethingElse() ; // Defined in B.CPP
}
include
কাজ করে?একটি ফাইল অন্তর্ভুক্ত করে, সংক্ষেপে, পার্স করে তারপরে সিপিপি ফাইলে এর বিষয়বস্তু অনুলিপি করে।
উদাহরণস্বরূপ, নিম্নলিখিত কোডে, A.HPP শিরোনাম সহ:
// A.HPP
void someFunction();
void someOtherFunction();
... উত্স বিসিপিপি:
// B.CPP
#include "A.HPP"
void doSomething()
{
// Etc.
}
... অন্তর্ভুক্তির পরে হয়ে উঠবে:
// B.CPP
void someFunction();
void someOtherFunction();
void doSomething()
{
// Etc.
}
বর্তমান ক্ষেত্রে, এটির প্রয়োজন নেই, এবং বিএইচপিপির doSomethingElse
ফাংশন ঘোষণা রয়েছে, এবং বিসিপিপি'র রয়েছেdoSomethingElse
ফাংশন সংজ্ঞা রয়েছে (যা নিজেই একটি ঘোষণা)। তবে আরও সাধারণ ক্ষেত্রে, যেখানে বিএইচপিপি ঘোষণার জন্য ব্যবহৃত হয় (এবং ইনলাইন কোড), সেখানে কোনও সংজ্ঞা সংজ্ঞা হতে পারে না (উদাহরণস্বরূপ, এনামস, প্লেইন স্ট্রাক্টস ইত্যাদি), সুতরাং বিসিপিপি অন্তর্ভুক্ত করার প্রয়োজন হতে পারে বিএইচপিপি থেকে এই ঘোষণা ব্যবহার করে। সব মিলিয়ে কোনও উত্সের ডিফল্টরূপে এর শিরোনাম অন্তর্ভুক্ত করা এটি "ভাল স্বাদ"।
শিরোনাম ফাইলটি এইভাবে প্রয়োজনীয়, কারণ সি ++ সংকলক একক প্রতীক ঘোষণার জন্য অনুসন্ধান করতে অক্ষম, এবং সুতরাং আপনাকে অবশ্যই এই ঘোষণাগুলি অন্তর্ভুক্ত করে এটি সহায়তা করতে হবে।
একটি শেষ কথা: একাধিক সংযোজন কোনও কিছু ভেঙে ফেলবে না তা নিশ্চিত হওয়ার জন্য আপনার এইচপিপি ফাইলগুলির সামগ্রীর চারপাশে হেডার গার্ড রাখা উচিত, তবে সর্বোপরি, আমি বিশ্বাস করি যে এইচপিপি ফাইলগুলির অস্তিত্বের মূল কারণটি উপরে ব্যাখ্যা করা হয়েছে।
#ifndef B_HPP_
#define B_HPP_
// The declarations in the B.hpp file
#endif // B_HPP_
বা এমনকি সহজ
#pragma once
// The declarations in the B.hpp file
You still have to copy paste the signature from header file to cpp file, don't you?
দরকার নেই। যতক্ষণ না সিপিপি এইচপিপি "অন্তর্ভুক্ত করে", পূর্বপরিবর্তক স্বয়ংক্রিয়ভাবে সিপিপি ফাইলে এইচপিপি ফাইলের বিষয়বস্তুগুলির অনুলিপি-পেস্ট করবে। আমি তা স্পষ্ট করে উত্তর আপডেট করেছি।
While compiling A.cpp, compiler knows the types of arguments and return value of doSomethingElse from the call itself
। না, তা হয় না। এটি কেবলমাত্র ব্যবহারকারী দ্বারা প্রদত্ত প্রকারগুলিই জানেন যা অর্ধেক সময় রিটার্ন মানটি পড়তেও বিরক্ত করবে না। তারপরে, অন্তর্নিহিত রূপান্তরগুলি ঘটে। এবং তারপরে, আপনার কাছে কোডটি রয়েছে: foo(bar)
আপনি foo
কোনও ফাংশন তা নিশ্চিতও করতে পারবেন না । সুতরাং উত্সটি সঠিকভাবে সংকলন করে কিনা তা নির্ধারণ করতে সংকলকটির শিরোনামে থাকা তথ্যের অ্যাক্সেস থাকতে হবে ... তারপর, কোডটি সংকলিত হয়ে গেলে, লিঙ্কারটি কেবল একসাথে ফাংশন কলগুলিতে লিঙ্ক করবে।
Seems, they're just a pretty ugly arbitrary design.
: যদি সত্যিই, সি ++ তৈরি করা হয়েছিল 2012 সালে। তবে মনে রাখবেন সি ++ এর উপরে 1980 এর দশকে নির্মিত হয়েছিল, এবং সেই সময় সীমাবদ্ধতাগুলি সে সময়ে বেশ আলাদা ছিল (আইআইআরসি, সি এর তুলনায় একই লিংকগুলি রাখার জন্য গ্রহণের উদ্দেশ্যে সিদ্ধান্ত নেওয়া হয়েছিল)।
foo(bar)
একটি ফাংশন - যদি এটি পয়েন্টার হিসাবে প্রাপ্ত হয়? আসলে, খারাপ ডিজাইনের কথা বললে, আমি সি ++ নয়, সি-কে দোষ দিই। খাঁটি সি এর কিছু প্রতিবন্ধকতা আমি সত্যিই পছন্দ করি না যেমন শিরোনাম ফাইল থাকা বা ফাংশনগুলি একটি এবং কেবল একটি মান ফেরত দেয়, ইনপুটটিতে একাধিক যুক্তি গ্রহণের সময় (ইনপুট এবং আউটপুট একইভাবে আচরণ করা স্বাভাবিক মনে হয় না) ; কেন একাধিক যুক্তি, তবে একক আউটপুট?) :)
Why can't I be sure, that foo(bar) is a function
একটি ধরণের হতে পারে, তাই আপনার কাছে একটি শ্রেণি নির্মাতা বলা হত। In fact, speaking of bad design, I blame C, not C++
: আমি অনেক কিছুর জন্য সি কে দোষ দিতে পারি, তবে 70 এর দশকে ডিজাইন করা সেগুলির মধ্যে একটি হবে না। আবার, সেই সময়ের সীমাবদ্ধতা ... such as having header files or having functions return one and only one value
: টিপলস এটিকে হ্রাস করতে সহায়তা করতে পারে, পাশাপাশি রেফারেন্স দিয়ে যুক্তিগুলি পাস করার ক্ষেত্রে। এখন, প্রত্যাবর্তিত একাধিক মান পুনরুদ্ধার করার সিনট্যাক্সটি কী হবে, এবং ভাষাটি পরিবর্তন করা কি উপযুক্ত হবে?
কারণ সি, যেখানে ধারণাটির উদ্ভব হয়েছিল 30 বছরের পুরনো এবং তারপরে, একাধিক ফাইলের কোডকে একসাথে যুক্ত করার একমাত্র কার্যকর উপায়।
আজ, এটি একটি ভয়াবহ হ্যাক যা সম্পূর্ণরূপে সি ++ এর সংকলন সময়কে ধ্বংস করে দেয়, অগণিত অহেতুক নির্ভরতা তৈরি করে (কারণ একটি শিরোনাম ফাইলে শ্রেণি সংজ্ঞা বাস্তবায়ন সম্পর্কে খুব বেশি তথ্য প্রকাশ করে) ইত্যাদি।
কারণ সি ++ এগুলি উত্তরাধিকার সূত্রে সি।
কারণ লাইব্রেরির ফর্ম্যাটটি ডিজাইন করা লোকেরা সি প্রিপ্রসেসর ম্যাক্রোস এবং ফাংশন ঘোষণার মতো বিরলভাবে ব্যবহৃত তথ্যের জন্য "অপচয়" করতে চান না।
আপনার সংকলকটি বলার জন্য যেহেতু আপনার সেই তথ্যের প্রয়োজন রয়েছে "লিঙ্কার যখন কাজ করছে তখন এই ফাংশনটি পরে পাওয়া যায়", তাই তাদের একটি দ্বিতীয় ফাইল নিয়ে আসতে হবে যেখানে এই ভাগ করা তথ্য সংরক্ষণ করা যেতে পারে।
সি / সি ++ এর পরে বেশিরভাগ ভাষাগুলি এই তথ্য আউটপুটে সংরক্ষণ করে (উদাহরণস্বরূপ জাভা বাইকোড) বা তারা কোনও পূর্বনির্ধারিত বিন্যাসটি ব্যবহার করে না, সর্বদা উত্স আকারে বিতরণ করে এবং ফ্লাইতে (পাইথন, পার্ল) সংকলন করে।
এটি ইন্টারফেস ঘোষণার প্রাকপ্রসেসর উপায়। আপনি শিরোনাম ফাইলে ইন্টারফেস (পদ্ধতি ঘোষণা) এবং সিপিসিতে প্রয়োগকরণ রেখেছেন। আপনার লাইব্রেরি ব্যবহার করে এমন অ্যাপ্লিকেশনগুলিকে কেবল ইন্টারফেসটি জানতে হবে, যা তারা # অন্তর্ভুক্তের মাধ্যমে অ্যাক্সেস করতে পারে।
প্রায়শই আপনি পুরো কোডটি শিপ না করে কোনও ইন্টারফেসের সংজ্ঞা রাখতে চান। উদাহরণস্বরূপ, আপনার যদি একটি ভাগ করা লাইব্রেরি থাকে তবে আপনি এটির সাথে একটি শিরোনাম ফাইল পাঠিয়ে দিন যা ভাগ করে নেওয়া লাইব্রেরিতে ব্যবহৃত সমস্ত কার্য এবং চিহ্নকে সংজ্ঞায়িত করে। শিরোলেখ ফাইলগুলি ছাড়া আপনার উত্সটি পাঠানো দরকার।
একটি একক প্রকল্পের মধ্যে, আইএমএইচও, অন্তত দুটি উদ্দেশ্যে হেডার ফাইলগুলি ব্যবহৃত হয়:
ম্যাডকিথভির উত্তরের প্রতিক্রিয়া ,
এটি নির্ভরতা হ্রাস করে যাতে শিরোনাম ব্যবহার করে এমন কোডগুলি প্রয়োগের সমস্ত বিবরণ এবং কেবল তার জন্য প্রয়োজনীয় অন্য কোনও শ্রেণি / শিরোনামগুলি জেনে রাখে না। এটি সংকলনের সময়গুলি এবং বাস্তবায়নের কোনও কিছু পরিবর্তিত হলে পুনঃসংশোধনের পরিমাণ হ্রাস করবে।
আরেকটি কারণ হ'ল একটি শিরোনাম প্রতিটি ক্লাসকে একটি অনন্য আইডি দেয়।
সুতরাং আমাদের মত কিছু আছে
class A {..};
class B : public A {...};
class C {
include A.cpp;
include B.cpp;
.....
};
আমাদের ত্রুটি থাকবে, যখন আমরা প্রকল্পটি তৈরির চেষ্টা করব, যেহেতু এ বি এর অংশ, তাই শিরোনাম সহ আমরা এই জাতীয় মাথাব্যথা এড়াতে পারি ...