জেনেরিকগুলি কীভাবে প্রয়োগ করা হয়?


16

এটি সংকলক অভ্যন্তরীণ দৃষ্টিকোণ থেকে প্রশ্ন।

আমি জেনেরিকগুলিতে আগ্রহী, টেম্পলেটগুলি (সি ++) নয়, তাই আমি প্রশ্নটি সি # দিয়ে চিহ্নিত করেছি। জাভা নয়, কারণ উভয় ভাষায় জেনেরিকগুলি বাস্তবায়নের ক্ষেত্রে আলাদা।

আমি যখন ডাব্লু / ও জেনেরিকগুলি ভাষা দেখি তবে এটি বেশ সোজা হয়, আপনি শ্রেণির সংজ্ঞাটি বৈধতা দিতে পারেন, এটিকে শ্রেণিবিন্যাসে যুক্ত করতে পারেন এবং এটিই।

তবে জেনেরিক ক্লাসটি কী করবেন এবং আরও গুরুত্বপূর্ণ এটির রেফারেন্সগুলি কীভাবে হ্যান্ডেল করবেন? স্থিতিশীল ক্ষেত্রগুলি প্রতি প্রতি ইনস্ট্যান্টেশনগুলিতে একক হয়ে রয়েছে তা নিশ্চিত করার জন্য (যেমন প্রতিবারের জেনেরিক পরামিতিগুলি সমাধান করা হয়)।

ধরা যাক আমি একটি কল দেখছি:

var x = new Foo<Bar>();

আমি Foo_Barকি শ্রেণিবিন্যাসে নতুন ক্লাস যুক্ত করব ?


আপডেট: এখনও অবধি আমি মাত্র 2 টি প্রাসঙ্গিক পোস্ট পেয়েছি, যদিও তারা "নিজের দ্বারা এটি কীভাবে করা যায়" অর্থে খুব বেশি বিবরণে যায় না:


উত্সাহ দেওয়া কারণ আমি মনে করি একটি সম্পূর্ণ উত্তর আকর্ষণীয় হবে। এটি কীভাবে কাজ করে সে সম্পর্কে আমার কিছু ধারণা আছে তবে সঠিক উত্তর দেওয়ার পক্ষে যথেষ্ট নয়। আমি মনে করি না যে সি # তে জেনেরিকগুলি প্রতিটি জেনেরিক ধরণের জন্য বিশেষায়িত ক্লাসগুলিতে সংকলন করে। এগুলি রানটাইমের সময়ে সমাধান হয়ে গেছে বলে মনে হচ্ছে (জেনেরিক ব্যবহারের ফলে লক্ষ্যণীয় গতি হতে পারে)। আমরা কি এরিক লিপার্টকে চিম ইন করতে পারি?
কেচালাক্স

2
@ ক্যালহাক্স: এমএসআইএল স্তরে জেনেরিকের একটি বর্ণনা রয়েছে। জেআইটি চললে, এটি জেনেরিক পরামিতি হিসাবে ব্যবহৃত প্রতিটি মান ধরণের জন্য পৃথক মেশিন কোড তৈরি করে এবং সমস্ত রেফারেন্সের প্রকারগুলি জুড়ে মেশিন কোডের আরও একটি সেট। এমএসআইএলে জেনেরিক বিবরণ সংরক্ষণ করা সত্যিই দুর্দান্ত কারণ এটি আপনাকে রানটাইমগুলিতে নতুন দৃষ্টান্ত তৈরি করতে দেয়।
বেন ভয়েগট


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

@Telastyn, ঐ বিষয়ের জন্য নিশ্চিত আমি :-) আমি কিছু জন্য, খুঁজছি আমি সত্যিই C # এর পাসে আমার ক্ষেত্রে আমি কম্পাইল করছি কাছে পিএইচপি (কোন রসিকতা)। আপনার জ্ঞান ভাগ করে নিলে আমি কৃতজ্ঞ হব।
গ্রীনল্ডম্যান

উত্তর:


4

স্থিতিশীল ক্ষেত্রগুলি প্রতি প্রতি ইনস্ট্যান্টেশনগুলিতে একক হয়ে রয়েছে তা নিশ্চিত করার জন্য (যেমন প্রতিবারের জেনেরিক পরামিতিগুলি সমাধান করা হয়)।

প্রতিটি জেনেরিক ইনস্ট্যান্টেশনের নিজস্ব কপি থাকে (বিভ্রান্তিমূলকভাবে নাম দেওয়া) মেথডটেবিল, যেখানে স্থির ক্ষেত্রগুলি সংরক্ষণ করা হয়।

ধরা যাক আমি একটি কল দেখছি:

var x = new Foo<Bar>();

আমি Foo_Barকি শ্রেণিবিন্যাসে নতুন ক্লাস যুক্ত করব ?

আমি নিশ্চিত নই যে এটি শ্রেণিবদ্ধতত্ত্ব সম্পর্কে কিছু কাঠামো যা আসলে রানটাইমের সময় বিদ্যমান, এটি যৌক্তিক নির্মাণের চেয়ে বেশি মনে করা দরকারী।

তবে আপনি যদি এই শ্রেণিবদ্ধতা গঠনের জন্য মেথডটেবিলগুলি প্রত্যেকে তার বেস শ্রেণিতে পরোক্ষ পয়েন্টার সহ বিবেচনা করেন, তবে হ্যাঁ, এটি শ্রেণিবিন্যাসে নতুন শ্রেণি যুক্ত করে।


আপনাকে ধন্যবাদ, এটি আকর্ষণীয় অংশ। সুতরাং স্থির ক্ষেত্রগুলি ভার্চুয়াল টেবিলের মতো একইভাবে সমাধান করা হবে, তাই না? "গ্লোবাল" অভিধানের জন্য একটি রেফারেন্স রয়েছে যা প্রতিটি প্রকারের জন্য এন্ট্রি রাখে? সুতরাং আমি 2 টি অ্যাসেমব্লি একে অপরকে ব্যবহার করে না জানার জন্য থাকতে পারি Foo<string>এবং তারা এ থেকে স্থির ক্ষেত্রের দুটি উদাহরণ তৈরি করতে পারে না Foo
গ্রীনল্ডম্যান

1
@ গ্রীনল্ডম্যান ভাল, ভার্চুয়াল টেবিলের মতো নয়, ঠিক একই রকম। মেথডেটেবল উভয় স্থিতিশীল ক্ষেত্র এবং প্রকারের পদ্ধতিগুলির রেফারেন্স ধারণ করে, যা ভার্চুয়াল প্রেরণে ব্যবহৃত হয় (এজন্য এটিকে মেথডটেবাল বলা হয়)। এবং হ্যাঁ, সিএলআরকে কিছু টেবিল থাকতে হবে যা এটি সমস্ত মেথডেটিবলগুলি অ্যাক্সেস করতে ব্যবহার করতে পারে।
এসভিক

2

আমি সেখানে দুটি আসল কংক্রিট প্রশ্ন দেখছি। সম্পূর্ণ বোঝার জন্য আপনি সম্ভবত অতিরিক্ত সম্পর্কিত প্রশ্ন জিজ্ঞাসা করতে চান (এটির জন্য একটি লিঙ্কের সাথে পৃথক প্রশ্ন হিসাবে) full

স্থির ক্ষেত্রগুলিকে কীভাবে জেনেরিক প্রতি পৃথক উদাহরণ দেওয়া হয়?

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

টাইপ প্যারামিটারের সাথে সম্পর্কিত সদস্য (স্থিতিশীল বা না) প্রকার মুছে ফেলার মাধ্যমে পরিচালনা করা যেতে পারে। সবচেয়ে শক্তিশালী বাধা যাই হোক না কেন ব্যবহার করুন (প্রায়শই System.Object)। সংকলক প্রকারের চেকের পরে প্রকারের তথ্য মুছে ফেলা হয়েছে বলে এর অর্থ রানটাইম টাইপ চেকের প্রয়োজন হবে না (যদিও ইন্টারফেসের ক্যাসেটগুলি রানটাইম এ এখনও বিদ্যমান থাকতে পারে)।

প্রতিটি জেনেরিক উদাহরণ পৃথকভাবে শ্রেণিবিন্যাসে প্রদর্শিত হয়?

নেট নেট জেনেরিক্সে নেই। সিদ্ধান্তটি প্যারামিটারগুলি টাইপ প্যারামিটার থেকে বাদ দেওয়ার জন্য করা হয়েছিল, সুতরাং দেখা যাচ্ছে যে জেনেরিকের সমস্ত দৃষ্টান্ত টাইপ শ্রেণিবিন্যাসের একই স্থান দখল করে।

এটি সম্ভবত একটি ভাল সিদ্ধান্ত ছিল, কারণ একটি বেস শ্রেণীর নাম অনুসন্ধানে ব্যর্থতা অবিশ্বাস্যরকম অবাক হবে।


আমার সমস্যাটি হ'ল আমি টেমপ্লেটের ক্ষেত্রে চিন্তাভাবনা থেকে দূরে থাকতে পারি না। উদাহরণ হিসেবে বলা যায় - অসদৃশ টেমপ্লেট জেনেরিক বর্গ হয় সম্পূর্ণরূপে কম্পাইল। এর অর্থ এই যে অন্যান্য সমাবেশে এই শ্রেণিটি ব্যবহার করে কী ঘটে? ইতিমধ্যে সংকলিত পদ্ধতিটি অভ্যন্তরীণ ingালাইয়ের সাথে ডাকা হয়? আমি সন্দেহ করি জেনারিকরা অন্যথায় যুক্তি - বাধা উপর নির্ভর করে নির্ভর করতে পারে Foo<int>এবং ডাব্লু / ও সীমাবদ্ধতার Foo<string>সাথে একই ডেটা Fooমারবে।
গ্রীনল্ডম্যান

1
@ গ্রীনল্ডম্যান: আমরা কী এক মিনিটের জন্য মূল্য ধরণের এড়াতে পারি, কারণ সেগুলি আসলে বিশেষভাবে পরিচালিত হয়? যদি আপনার থাকে List<string>এবং List<Form>, যেহেতু List<T>অভ্যন্তরীণভাবে টাইপের সদস্য রয়েছে T[]এবং এতে কোনও বাধা নেই T, তবে আপনি আসলে যা পাবেন সেটি মেশিন কোড যা একটি ম্যানিপুলেট করে object[]। তবে, যেহেতু কেবলমাত্র Tউদাহরণগুলিকে অ্যারেতে রাখা হয়েছে, তাই প্রকাশিত সমস্ত কিছু Tঅতিরিক্ত ধরণের চেক ব্যতীত ফেরত দেওয়া যেতে পারে । অন্যদিকে, আপনি যদি থাকেন ControlCollection<T> where T : Controlতবে অভ্যন্তরীণ অ্যারেটি T[]হয়ে যাবে Control[]
বেন ভয়েগট

আমি কি সঠিকভাবে বুঝতে পারি যে, এই সীমাবদ্ধতাটি অভ্যন্তরীণ টাইপনেম হিসাবে নেওয়া হয় এবং ব্যবহৃত হয়, কিন্তু যখন শ্রেণিটি আসলে ব্যবহৃত হয় তখন ingালাই ব্যবহৃত হয়? ঠিক আছে, আমি সেই মডেলটি বুঝতে পারি, তবে আমি জাভা এটি ব্যবহার করে এমন ছাপের মধ্যে ছিল, সি # নয়।
গ্রীনল্ডম্যান

3
@ গ্রেইনলডম্যান: জাভা উত্স-> বাইটকোড অনুবাদ ধাপে ধরণের মুছে ফেলা সম্পাদন করে। যা যাচাইকারীর পক্ষে জেনেরিক কোড যাচাই করা অসম্ভব করে তোলে। সি # এটি বাইটকোড-> মেশিন কোড ধাপে করে।
বেন ভয়েগট

@ বেনভয়েগ্ট জেনেরিক ধরণের সম্পর্কে জাভাতে কিছু তথ্য বজায় রাখা হয়, অন্যথায় আপনি জেনেরিক-ব্যবহারের শ্রেণীর উত্স ছাড়াই সংকলন করতে পারবেন না। এটি কেবলমাত্র বাইকোড সিকোয়েন্সেই এআইআইআইআইতে রাখা হয়নি, বরং ক্লাস মেটাডেটাতে।
ডোনাল ফেলো

1

তবে জেনেরিক ক্লাসটি কী করবেন এবং আরও গুরুত্বপূর্ণ এটির রেফারেন্সগুলি কীভাবে হ্যান্ডেল করবেন?

সংকলকটির সামনের প্রান্তের সাধারণ উপায়ে দুটি ধরণের ধরণের দৃষ্টান্ত রয়েছে, জেনেরিক টাইপ ( List<T>) এবং একটি সীমাবদ্ধ জেনেরিক প্রকার ( List<Foo>)। জেনেরিক টাইপটি কোন ফাংশন বিদ্যমান, কোন ক্ষেত্রগুলি এবং যেখানেই Tব্যবহৃত হয় জেনেরিক প্রকারের রেফারেন্স নির্ধারণ করে। সীমাবদ্ধ জেনেরিক টাইপটিতে জেনেরিক ধরণের একটি রেফারেন্স এবং টাইপ আর্গুমেন্টের সেট থাকে। এরপরে একটি কংক্রিটের ধরণের উত্পন্ন করার জন্য আপনার কাছে পর্যাপ্ত তথ্য রয়েছে, জেনেরিক ধরণের রেফারেন্সগুলির সাথে প্রতিস্থাপন করুন Fooবা টাইপ আর্গুমেন্টগুলি যাই হোক না কেন। এই ধরণের পার্থক্যটি গুরুত্বপূর্ণ যখন আপনি টাইপ অনুক্রমটি করছেন এবং List<T>বিপরীতে অনুমান করা দরকার List<Foo>

টেম্পলেটগুলির মতো জেনেরিকের কথা চিন্তা না করে (যা সরাসরি বিভিন্ন বাস্তবায়ন তৈরি করে) এর পরিবর্তে ফাংশনাল ল্যাঙ্গুয়েজ টাইপ কনস্ট্রাক্টর (যেখানে জেনেরিক আর্গুমেন্টগুলি আপনাকে কোনও প্রকার দেয় এমন আর্গুমেন্টের মতো) মনে করার পরিবর্তে এটি সহায়ক হতে পারে।

পিছনের প্রান্ত হিসাবে, আমি সত্যিই জানি না। জেনেরিক্স সহ আমার সমস্ত কাজ ব্যাকেন্ড হিসাবে সিআইএলকে টার্গেট করেছে, তাই আমি সেগুলি সেখানে সমর্থিত জেনারিকগুলিতে সংকলন করতে পারি।


আপনাকে অনেক ধন্যবাদ (করুণা আমি বহুগুণ উত্তর গ্রহণ করতে পারি না)। এটা শুনে আমি দুর্দান্ত যে আমি সেই পদক্ষেপটি সঠিকভাবেই করেছি - আমার ক্ষেত্রে List<T>আসল ধরণ রয়েছে (এর সংজ্ঞা), তবে List<Foo>(পরিভাষা টুকরোটির জন্য আপনাকে ধন্যবাদও) আমার পদ্ধতির সাথে List<T>(অবশ্যই এখন আবদ্ধ Fooপরিবর্তে T)।
গ্রীনল্ডম্যান 21
আমাদের সাইট ব্যবহার করে, আপনি স্বীকার করেছেন যে আপনি আমাদের কুকি নীতি এবং গোপনীয়তা নীতিটি পড়েছেন এবং বুঝতে পেরেছেন ।
Licensed under cc by-sa 3.0 with attribution required.