সেট () কীভাবে প্রয়োগ করা হয়?


151

আমি লোককে বলতে দেখেছি যে setঅজগরের বস্তুগুলির O (1) সদস্যপদ-পরীক্ষা রয়েছে। এটি অনুমতি দেওয়ার জন্য তারা কীভাবে অভ্যন্তরীণভাবে প্রয়োগ করা হয়? এটি কোন ধরণের ডেটা স্ট্রাকচার ব্যবহার করে? এই বাস্তবায়নের অন্যান্য কী কী প্রভাব রয়েছে?

এখানে প্রতিটি উত্তর সত্যই আলোকিত ছিল, তবে আমি কেবল একটি গ্রহণ করতে পারি, তাই আমি আমার মূল প্রশ্নের নিকটতম উত্তর নিয়ে যাব। তথ্যের জন্য সকলকে ধন্যবাদ!

উত্তর:


139

এই থ্রেড অনুযায়ী :

প্রকৃতপক্ষে সিপিথনের সেটগুলি ডেমি মানগুলির সাথে (অভিধানের সদস্য হিসাবে থাকা কীগুলি) অভিধানের মতো কিছু হিসাবে প্রয়োগ করা হয়, কিছু অপ্টিমাইজেশন (গুলি) যা মানগুলির এই অভাবকে কাজে লাগায়

সুতরাং মূলত একটি setএর অন্তর্নিহিত ডেটা কাঠামো হিসাবে একটি হ্যাশটেবল ব্যবহার করে। এটি ও (1) সদস্যতার চেকিংয়ের ব্যাখ্যা করে, যেহেতু হ্যাশটেবলে কোনও আইটেম সন্ধান করা একটি ও (1) ক্রিয়াকলাপ।

আপনি যদি এত ঝুঁকে থাকেন তবে আপনি সিপিথন উত্স কোডটি সেটের জন্যও ব্রাউজ করতে পারেন যা আচিম ডোমমার মতে , বেশিরভাগ dictবাস্তবায়ন থেকে কাট-পেস্ট ।


18
আইআইআরসি, মূল setবাস্তবায়নটি ছিল dict ডামি মানগুলির সাথে, এবং এটি পরে অনুকূলিত হয়েছিল।
dan04

1
সবচেয়ে বড় পরিস্থিতি কি সবচেয়ে খারাপ নয়? সময়টি ও (এন) যেখানে আপনি যদি কোনও উদাহরণ খুঁজে পেতে পারেন তবে তা ও (এন) .. এই সমস্ত টিউটোরিয়াল থেকে আমি এখনই কিছু বুঝতে পারি না।
ক্লদিউ ক্রিঙ্গা

4
না, গড় কেস ও (1) তবে হ্যাশ টেবিল দেখার জন্য সবচেয়ে খারাপ ক্ষেত্রে ও (এন)।
জাস্টিন এথিয়ের

4
@ ক্লাউডিউ ক্রাইঙ্গা এটি একটি পুরানো মন্তব্য, তবে কেবল স্পষ্ট করে বলার জন্য: বিগ-ও নোটেশন আপনাকে জিনিসগুলির বৃদ্ধির হারের উপরের সীমাটি বলছে, তবে আপনি গড় কেস কর্মক্ষমতা বৃদ্ধির উপরের সীমাবদ্ধ করতে পারেন এবং আপনি পৃথকভাবে খারাপ অবস্থার বর্ধনের উপরের সীমানা করতে পারেন কর্মক্ষমতা.
বায়ার

79

লোকেরা যখন সেটগুলিতে ও (1) সদস্যপদ-যাচাই করে থাকে বলে তারা গড় মামলার বিষয়ে কথা বলে । সবচেয়ে খারাপ ক্ষেত্রে (যখন সমস্ত হ্যাশ মানগুলি সংঘর্ষ হয়) সদস্যপদ-চেকিং হল ও (এন)। সময় জটিলতায় পাইথন উইকি দেখুন ।

Wikipedia নিবন্ধটি বলছেন সেরা ক্ষেত্রে একটি হ্যাশ টেবিল পুনরায় আকার দেওয়ার হয় না যে, সময় জটিলতা O(1 + k/n)। এই ফলাফলটি পাইথন সেটগুলিতে সরাসরি প্রয়োগ হয় না যেহেতু পাইথন সেটগুলি হ্যাশ টেবিল ব্যবহার করে যা আকার পরিবর্তন করে।

উইকিপিডিয়া নিবন্ধের সামান্য আরও বলা হয়েছে যে গড় ক্ষেত্রে, এবং একটি সাধারণ ইউনিফর্ম হ্যাশিং ফাংশন ধরে নিয়ে সময় জটিলতা O(1/(1-k/n)), যেখানে k/nধ্রুবক দ্বারা আবদ্ধ হতে পারে c<1

বিগ-ও কেবলমাত্র y ∞ হিসাবে asympotic আচরণ বোঝায় ∞ যেহেতু k / n একটি ধ্রুবক দ্বারা আবদ্ধ হতে পারে, সি <1, এন থেকে পৃথক ,

O(1/(1-k/n))= এর O(1/(1-c))সমান কোনটি বড় নয় ।O(constant)O(1)

সুতরাং ইউনিফর্ম সিম্পল হ্যাশিং ধরে নেওয়া, গড়ে পাইথন সেটগুলির জন্য সদস্যতা-পরীক্ষা করা O(1)


14

আমি মনে করি এটি একটি সাধারণ ভুল, setঅনুসন্ধান (বা সেই বিষয়ে হ্যাশটেবল) ও (1) নয়।
উইকিপিডিয়া থেকে

সহজতম মডেলটিতে হ্যাশ ফাংশনটি সম্পূর্ণ অনির্দিষ্ট এবং টেবিলটির আকার পরিবর্তন হয় না। হ্যাশ ফাংশনটির সর্বোত্তম পছন্দের জন্য, উন্মুক্ত ঠিকানা সহ মাপের একটি টেবিলের কোনও সংঘর্ষ নেই এবং সফল অনুসন্ধানের জন্য একক তুলনা সহ এন উপাদানগুলি ধরে আছে, এবং চেইনিং এবং কে কী সহ আকারের এন টেবিলের ন্যূনতম সর্বোচ্চ রয়েছে (0, ন) সংঘর্ষ এবং ও (1 + কে / এন) দেখার জন্য তুলনা। হ্যাশ ফাংশনটির সবচেয়ে খারাপ নির্বাচনের জন্য, প্রতিটি সন্নিবেশ একটি সংঘর্ষের কারণ হয়ে থাকে এবং হ্যাশ টেবিলগুলি সন্ধানের জন্য সন্নিবেশিত am (কে) স্বল্প পরিমাণে এবং সফল অনুসন্ধানের জন্য কে পর্যন্ত তুলনা করে লিনিয়ার সন্ধানে অধঃপতিত হয়।

সম্পর্কিত: একটি জাভা হ্যাশম্যাপ আসলেই ও (1)?


4
তবে তারা আইটেমগুলি সন্ধান করতে অবিচ্ছিন্ন সময় নেয়: পাইথন-মি টাইমিট-এস "এস = সেট (পরিসীমা (10))" "এস 5" 10000000 লুপ, প্রতি লুপে 3: 0.0642 ইউজিক <--> পাইথন - মি টাইমিট-এস "এস = সেট (পরিসীমা (10000000))" "এস ইন 5" 10000000 লুপ, প্রতি লুপে 3: 0.0634 ইউজিকের সেরা ... এবং এটিই সবচেয়ে বড় সেট যা মেমোরিএরগুলি ফেলে না
জোচেন

2
@ THC4k আপনার প্রমাণিত সমস্তটি হ'ল এক্স সন্ধান করা ধ্রুবক সময়ে সম্পন্ন হয় তবে এর অর্থ এই নয় যে এক্স + ওয়াই সন্ধান করার সময় একই পরিমাণে সময় নেবে যা ও (1) এর সমান।
শাই এরলিচম্যান

3
@ চিহ্নযুক্ত: এটি রয়েছে, তবে উপরের পরীক্ষাটি প্রমাণ করে না যে আপনি একই সাথে "485398" বা অন্য কোনও সংখ্যার সন্ধান করতে পারেন যা আপনি একটি ভয়াবহ সংঘর্ষের জায়গায় থাকতে পারেন you এটি একই সময়ে ভিন্ন আকারের হ্যাশগুলিতে একই উপাদানটি অনুসন্ধান করার বিষয়ে নয় (আসলে এটির প্রয়োজন হয় না), তবে বর্তমান টেবিলে আপনি একই পরিমাণে প্রতিটি এন্ট্রি অ্যাক্সেস করতে পারবেন কিনা তা সম্পর্কে - হ্যাশ টেবিলগুলির পক্ষে এটি সাধারনত অসম্ভব যেহেতু সাধারণত সর্বদা সংঘর্ষ হয়।
নিক বাস্টিন

3
অন্য কথায়, একটি অনুসন্ধান করার সময়টি সঞ্চিত মানগুলির সংখ্যার উপর নির্ভর করে, কারণ এটি সংঘর্ষের সম্ভাবনা বৃদ্ধি করে।
16:53

3
@ সংযুক্ত: না, এটি ভুল। যখন সঞ্চিত মানের সংখ্যা বৃদ্ধি পায়, পাইথন স্বয়ংক্রিয়ভাবে হ্যাশটেবলের আকার বাড়িয়ে তুলবে এবং সংঘর্ষের হার মোটামুটি স্থির থাকে। একটি সমানভাবে বিতরণ হে (1) হ্যাশ অ্যালগরিদম ধরে নেওয়া যাক, তারপর hashtable লুকআপ হয় amortized হে (1)। আপনি ভিডিও উপস্থাপনাটি "দ্য মাইটি ডিকশনারি" দেখতে দেখতে চাইতে পারেন পাইথন.মিরোকমমিউটি.আর
লাই রায়ান

13

আমরা সব সহজ এক্সেস আছে উৎস , যেখানে মন্তব্য পূর্ববর্তী set_lookkey()বলেছেন:

/* set object implementation
 Written and maintained by Raymond D. Hettinger <python@rcn.com>
 Derived from Lib/sets.py and Objects/dictobject.c.
 The basic lookup function used by all operations.
 This is based on Algorithm D from Knuth Vol. 3, Sec. 6.4.
 The initial probe index is computed as hash mod the table size.
 Subsequent probe indices are computed as explained in Objects/dictobject.c.
 To improve cache locality, each probe inspects a series of consecutive
 nearby entries before moving on to probes elsewhere in memory.  This leaves
 us with a hybrid of linear probing and open addressing.  The linear probing
 reduces the cost of hash collisions because consecutive memory accesses
 tend to be much cheaper than scattered probes.  After LINEAR_PROBES steps,
 we then use open addressing with the upper bits from the hash value.  This
 helps break-up long chains of collisions.
 All arithmetic on hash should ignore overflow.
 Unlike the dictionary implementation, the lookkey function can return
 NULL if the rich comparison returns an error.
*/


...
#ifndef LINEAR_PROBES
#define LINEAR_PROBES 9
#endif

/* This must be >= 1 */
#define PERTURB_SHIFT 5

static setentry *
set_lookkey(PySetObject *so, PyObject *key, Py_hash_t hash)  
{
...

2
এই উত্তরটি সি সিনট্যাক্স হাইলাইট করে উপকৃত হবে । মন্তব্যটির পাইথন সিনট্যাক্স হাইলাইট করা সত্যিই খারাপ দেখাচ্ছে।
ব্যবহারকারী 202729

"এটি আমাদেরকে লিনিয়ার প্রোবিং এবং ওপেন অ্যাড্রেসিংয়ের একটি সংকর দিয়ে ফেলেছে" মন্তব্য সম্পর্কে, এন.ইউইকিপিডিয়া.আর / উইকি / ওপেন_ড্রেসিংয়ে বর্ণিত লাইন কি খোলা ঠিকানায় এক ধরণের সংঘর্ষের সমাধানের অনুসন্ধান করে না ? অতএব, লিনিয়ার প্রোবিং হ'ল খোলা সম্বোধনের একটি উপপ্রকার এবং মন্তব্যটি কোনও অর্থ দেয় না।
অ্যালান ইভাঞ্জেলিস্ট

2

set'sএবং এর মধ্যে আরও কয়েকটি পার্থক্যের উপর জোর দেওয়ার জন্য dict's, এখানে setobject.cমন্তব্য বিভাগগুলির একটি অংশ এখানে দেওয়া হয়েছে , যা স্পষ্ট করে দেয় সেটগুলির মূল পার্থক্যের বিরুদ্ধে ডিক্টস।

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

গিথুব উপর উত্স

আমাদের সাইট ব্যবহার করে, আপনি স্বীকার করেছেন যে আপনি আমাদের কুকি নীতি এবং গোপনীয়তা নীতিটি পড়েছেন এবং বুঝতে পেরেছেন ।
Licensed under cc by-sa 3.0 with attribution required.