পাইথনে "বিপরীত" তালিকা তৈরি করার সর্বোত্তম উপায়?


92

পাইথনে, নতুন তালিকা তৈরির সর্বোত্তম উপায় কী যার আইটেমগুলি অন্য কয়েকটি তালিকার মতো, তবে বিপরীত ক্রমে? (আমি বিদ্যমান তালিকাকে সঠিকভাবে সংশোধন করতে চাই না))

এখানে আমার কাছে একটি সমাধান এসেছে:

new_list = list(reversed(old_list))

old_listসদৃশ করা যায় এবং তার পরে নকলটি উল্টো করে দেওয়া সম্ভব :

new_list = list(old_list) # or `new_list = old_list[:]`
new_list.reverse()

আমি উপেক্ষা করেছি এর চেয়ে ভাল বিকল্প আছে? যদি তা না হয় তবে উপরোক্ত পদ্ধতির একটিটিকে অপরটির চেয়ে বেশি ব্যবহার করার জন্য কি বাধ্যতামূলক কারণ (যেমন দক্ষতা) রয়েছে?

উত্তর:


208
newlist = oldlist[::-1]

[::-1]Slicing (যা আমার স্ত্রী আন্না "মঙ্গল স্মাইলি" ;-) উপায়ে কল লেগেছে: ছে পুরো ক্রম -1 পদক্ষেপ, অর্থাত, বিপরীত সঙ্গে। এটি সব সিকোয়েন্সের জন্য কাজ করে।

মনে রাখবেন যে এটি ( এবং বিকল্পগুলি আপনি উল্লিখিত) একটি "অগভীর অনুলিপি" এর সমান, অর্থাত্: যদি আইটেমগুলি পরিবর্তনযোগ্য হয় এবং আপনি সেগুলিকে মিউটরদের কল করেন তবে মূল তালিকায় থাকা আইটেমগুলির পরিব্যক্তিগুলিও আইটেমের মধ্যে রয়েছে বিপরীত তালিকা, এবং বিপরীত। যদি আপনার এড়াতে প্রয়োজন হয় copy.deepcopyতবে এ (এ ক্ষেত্রে সর্বদা সম্ভাব্য ব্যয়বহুল অপারেশন) .reverseহ'ল একমাত্র ভাল বিকল্প।


আহারে! যে হয় মার্জিত। কিছু দিন আগে আমি বুঝতে পারি নি যে টুকরো টুকরো করার সময় কোনও "পদক্ষেপ" অন্তর্ভুক্ত করা সম্ভব; এখন আমি ভাবছি কীভাবে আমি এটিকে ছাড়াই পেলাম! ধন্যবাদ, অ্যালেক্স :)
ডেভিডচেম্বার

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

13
এটি প্রকৃত পরামর্শের চেয়ে অনেক বেশি যাদু এবং অনেক কম পাঠযোগ্য বলে মনে হচ্ছে list(reversed(oldlist))। গৌণ মাইক্রো-অপটিমাইজেশন বাদে, পছন্দ [::-1]করার কোনও কারণ আছে reversed()কি?
ব্রায়ান ক্যাম্পবেল

@ ব্রায়ান ক্যাম্পবেল: এটি সম্পর্কে "যাদু" কী? আপনি যদি টুকরো টুকরো টুকরোটি বুঝতে পারেন তবে এটি মোটামুটি অর্থপূর্ণ। যদি আপনি কাটা কাটা বুঝতে না পারেন ... ভাল, আপনার পাইথন ক্যারিয়ারের শুরুতে আপনার এটি খুব শিখতে হবে। অবশ্যই reversedএকটি বিশাল সুবিধা যখন আপনি রয়েছেন না , তালিকা প্রয়োজন এটি মেমরি বা আপ ফ্রন্ট সময় এটি নির্মাণের অপচয় না কারণ। কিন্তু আপনি যখন না তালিকা প্রয়োজন ব্যবহার [::-1]পরিবর্তে list(reversed())ব্যবহার করে একটি অনুরূপ [listcomp]পরিবর্তে list(genexpr)
অবতারিত

11
@ বার্নার্ট আমি যে কোডটি দিয়ে কাজ করছি তাতে আমি খুব কমই তৃতীয় স্লাইস যুক্তিটি দেখতে পাই, যদি আমি এর ব্যবহার দেখতে পাই তবে এর অর্থ কী তা বোঝাতে হবে। আমি একবার করলে, এটি এখনও স্পষ্ট নয় যে যখন ধাপটি নেতিবাচক হয় তখন ডিফল্ট শুরু এবং শেষের মানগুলি অদলবদল হয়। তাত্ক্ষণিকভাবে তৃতীয় তর্কের অর্থটি অনুসন্ধান না করেই আমি অনুমান করতে পারি যে [::-1]এটির পরিবর্তনের পরিবর্তে তালিকার শেষ উপাদানটি অপসারণ করা উচিত। reversed(list)ঠিক কি করছে তা জানিয়েছে; এটি "অভিহিতের চেয়ে সুস্পষ্ট ভাল", "পঠনযোগ্যতা গণনা", এবং "স্পর্শে ঘন চেয়ে ভাল" অর্থে এটি তার অভিপ্রায়টি ব্যাখ্যা করে।
ব্রায়ান ক্যাম্পবেল

56

এখন চলুন timeitইঙ্গিত: অ্যালেক্স [::-1]দ্রুততম :)

$ p -m timeit "ol = [1, 2, 3]; nl = list(reversed(ol))"
100000 loops, best of 3: 2.34 usec per loop

$ p -m timeit "ol = [1, 2, 3]; nl = list(ol); nl.reverse();"
1000000 loops, best of 3: 0.686 usec per loop

$ p -m timeit "ol = [1, 2, 3]; nl = ol[::-1];"
1000000 loops, best of 3: 0.569 usec per loop

$ p -m timeit "ol = [1, 2, 3]; nl = [i for i in reversed(ol)];"
1000000 loops, best of 3: 1.48 usec per loop


$ p -m timeit "ol = [1, 2, 3]*1000; nl = list(reversed(ol))"
10000 loops, best of 3: 44.7 usec per loop

$ p -m timeit "ol = [1, 2, 3]*1000; nl = list(ol); nl.reverse();"
10000 loops, best of 3: 27.2 usec per loop

$ p -m timeit "ol = [1, 2, 3]*1000; nl = ol[::-1];"
10000 loops, best of 3: 24.3 usec per loop

$ p -m timeit "ol = [1, 2, 3]*1000; nl = [i for i in reversed(ol)];"
10000 loops, best of 3: 155 usec per loop

আপডেট: ইন্সপেক্টর জি 4ডেজে প্রস্তাবিত তালিকার কমপ পদ্ধতিটি। আমি ফলাফলগুলি তাদের পক্ষে কথা বলতে দেব।


8
কেবল একটি নোট - বিপরীত অনুলিপি তালিকা তৈরি করার জন্য এটি সঠিক তবে [::-1]
বিপরীতটি

7

সামঞ্জস্য

Sdolan দ্বারা সময়কাল গণনার জন্য একটি বেসলাইন বেঞ্চমার্ক / সামঞ্জস্য প্রদান করা উপযুক্ত যা প্রায়শই অপ্রয়োজনীয় list()রূপান্তর ছাড়াই 'বিপরীত' এর পারফরম্যান্স দেখায় । এই list()অপারেশনটি রানটাইমে অতিরিক্ত 26 ইউজিসিএস যুক্ত করে এবং কেবলমাত্র ইভেন্টের ক্ষেত্রে প্রয়োজন যখন কোনও পুনরাবৃত্তি গ্রহণযোগ্য নয়।

ফলাফল:

reversed(lst) -- 11.2 usecs

list(reversed(lst)) -- 37.1 usecs

lst[::-1] -- 23.6 usecs

গণনা:

# I ran this set of 100000 and came up with 11.2, twice:
python -m timeit "ol = [1, 2, 3]*1000; nl = reversed(ol)"
100000 loops, best of 3: 11.2 usec per loop

# This shows the overhead of list()
python -m timeit "ol = [1, 2, 3]*1000; nl = list(reversed(ol))"
10000 loops, best of 3: 37.1 usec per loop

# This is the result for reverse via -1 step slices
python -m timeit "ol = [1, 2, 3]*1000;nl = ol[::-1]"
10000 loops, best of 3: 23.6 usec per loop

উপসংহার:

এই পরীক্ষাগুলির উপসংহারটি 12.4 ইউজিক দ্বারা reversed()স্লাইসের চেয়ে দ্রুত[::-1]


15
বিপরীত () একটি পুনরাবৃত্ত বস্তু দেয় যা অলস-মূল্যায়ন করা হয়, সুতরাং আমি মনে করি এটি সাধারণভাবে কাটা সংকেত [:: - 1] এর সাথে তুলনামূলকভাবে তুলনামূলক নয়।
চিত্রাভ

4
এমনকি কোনও ক্ষেত্রে যখন কোনও পুনরুক্তিকারী সরাসরি ব্যবহার করা যায় যেমন ''.join(reversed(['1','2','3']))স্লাইস পদ্ধতিটি এখনও 30% দ্রুত হয়।
ডানসালমো

4
প্রথম 2 টি পরীক্ষায় কেন আপনি একই ফলাফল পেয়েছিলেন তা অবাক হওয়ার কিছু নেই: তারা অভিন্ন!
MestreLion

আমার ফলাফলগুলি এর সাথে আরও সাদৃশ্যপূর্ণ। # [:: - 1] তালিকা হিসাবে প্রায় দ্বিগুণ সময় নেয় (বিপরীত (ওল))। # [:: - 1] পদ্ধতিটি লিখতে কম অক্ষর লাগে। তবে তালিকা (বিপরীত (ওল্ড)) সম্ভবত প্রাথমিক অজগর প্রোগ্রামারদের জন্য আরও পঠনযোগ্য এবং এটি আমার মেশিনে দ্রুত is
dhj
আমাদের সাইট ব্যবহার করে, আপনি স্বীকার করেছেন যে আপনি আমাদের কুকি নীতি এবং গোপনীয়তা নীতিটি পড়েছেন এবং বুঝতে পেরেছেন ।
Licensed under cc by-sa 3.0 with attribution required.