পাইথনে x [x <2] = 0 এর অর্থ কী?


85

আমি কিছু কোড জুড়ে এসেছি যার মতো একটি লাইন রয়েছে

x[x<2]=0

বিভিন্নতা নিয়ে ঘুরে বেড়াতে, আমি এখনও এই বাক্য গঠনটি কী করে তাতে আটকা পড়েছি।

উদাহরণ:

>>> x = [1,2,3,4,5]
>>> x[x<2]
1
>>> x[x<3]
1
>>> x[x>2]
2
>>> x[x<2]=0
>>> x
[0, 2, 3, 4, 5]

7
কোনও তালিকা দিয়ে এটি করা কখনই বোধগম্য নয়।
dbliss

12
এটি কেবলমাত্র NumPy অ্যারে বা অনুরূপ অবজেক্টের সাথেই বোঝাপড়া করে, যা আপনার পরীক্ষাগুলিতে বা তালিকার ভিত্তিক আচরণের থেকে উত্তরে বর্ণিত আলাদাভাবে আচরণ করে either
ব্যবহারকারী 2357112 মনিকা

11
দ্রষ্টব্য, পাইথন 3 এ এটি কাজ করে না প্রকারের তুলনাটি বোধগম্য হলে কেবল তুলনা করতে সক্ষম। পাইথন 3 এ এই উদাহরণটি ছুঁড়েছে TypeError: unorderable types: list() < int()
মরগান থ্রাপ

4
খুব অল্প তথ্য। অ্যারেটি একটি অদ্ভুত অ্যারে উল্লেখ করা উচিত ছিল।
lmaooooo

4
আমি এতে প্রচুর উত্সাহ পেয়েছি (যদিও এটি সত্যই এটি ফর্ম্যাটের জন্য একটি ভাল প্রশ্ন) shocked
পাসক্যালভিকুটেন

উত্তর:


120

এটি কেবল NumPy অ্যারে দিয়েই বোঝা যায় । তালিকাগুলি সহ আচরণটি অকেজো এবং পাইথন 2 এর সাথে নির্দিষ্ট (পাইথন 3 নয়)। আপনি ডাবল-চেক করতে চাইতে পারেন যে আসল বস্তুটি আসলেই একটি NumPy অ্যারে ছিল (নীচে আরও দেখুন) এবং তালিকাটি নয়।

তবে আপনার কোডে এখানে x একটি সাধারণ তালিকা।

থেকে

x < 2

মিথ্যা অর্থাৎ 0, তাই

x[x<2] হয় x[0]

x[0] বদলে যায়

বিপরীতে, x[x>2]হয় x[True]বাx[1]

সুতরাং, x[1]পরিবর্তিত হয়।

কেন এমন হয়?

তুলনার নিয়মগুলি হ'ল:

  1. আপনি যখন দুটি স্ট্রিং বা দুটি সংখ্যার প্রকারের অর্ডার করেন তখন প্রত্যাশিত উপায়ে অর্ডারিং হয় (স্ট্রিংয়ের জন্য ডিক্সিকোগ্রাফিক ক্রম, পূর্ণসংখ্যার জন্য সংখ্যাগত ক্রম)।

  2. আপনি যখন একটি সংখ্যাসূচক এবং একটি অ-সংখ্যািক প্রকার অর্ডার করেন, তখন প্রথম সংখ্যাটি প্রথম আসে type

  3. আপনি যখন দুটি বেমানান প্রকারের অর্ডার করেন যেখানে কোনওটিই সংখ্যাসূচক নয়, সেগুলি তাদের টাইপের নামগুলির বর্ণমালা অনুসারে অর্ডার করা হয়:

সুতরাং, আমরা নিম্নলিখিত আদেশ আছে

সংখ্যার <তালিকা <স্ট্রিং <tuple

পাইথন স্ট্রিং এবং ইনটকে কীভাবে তুলনা করে তার জন্য গৃহীত উত্তর দেখুন ?

যদি x একটি NumPy অ্যারে হয় , তবে বুলিয়ান অ্যারে সূচকের কারণে সিনট্যাক্সটি আরও অর্থবোধ করে । সেক্ষেত্রে, x < 2এ সব একটি বুলিয়ান নয়; এটি বুলিয়ানগুলির একটি অ্যারে প্রতিনিধিত্ব করে যা প্রতিটি উপাদান 2 এর xচেয়ে কম ছিল কিনা x[x < 2] = 0তারপরে তার উপাদানগুলি x2 এর চেয়ে কম ছিল এবং সেগুলি সেলকে 0 এ সেট করে Ind সূচীকরণ দেখুন ।

>>> x = np.array([1., -1., -2., 3])
>>> x < 0
array([False,  True,  True, False], dtype=bool)
>>> x[x < 0] += 20   # All elements < 0 get increased by 20
>>> x
array([  1.,  19.,  18.,   3.]) # Only elements < 0 are affected

11
প্রদত্ত যে ওপি বিশেষত "আমি এর মতো কিছু কোড জুড়ে এসেছি ..." বলে আমি মনে করি যে নম্পি বুলিয়ান সূচকে বর্ণনা করা আপনার উত্তরটি খুব দরকারী - এটি উল্লেখ করার মতো হতে পারে যে ওপি যদি তারা যে কোডটি দেখেছিল সেগুলি সরিয়ে ফেললে তারা ' প্রায় importঅবাক হয়ে একটি দেখতে পাবেন।
জে রিচার্ড স্নেপ

4
এখনও এটি করার একটি অত্যধিক চতুর উপায়, অবশ্যই? (এর সাথে তুলনা করুন, বলুন [0 if i < 2 else i for i in x]।) বা এই নম্প্পিতে উত্সাহিত শৈলী?
টিম পেডারিক

6
@ টিমপিডেরিক: নুমপির সাথে তালিকা বোঝার ব্যবহার করা একটি খুব খারাপ ধারণা is এটি কয়েক ডজন থেকে কয়েকগুণ ধীর গতিযুক্ত, এটি স্বেচ্ছাকৃতির-মাত্রিক অ্যারেগুলির সাথে কাজ করে না, উপাদানগুলির ধরণগুলি আরও সহজে তৈরি করা সহজ এবং এটি অ্যারের পরিবর্তে একটি তালিকা তৈরি করে। বুলিয়ান অ্যারে সূচকগুলি সম্পূর্ণ স্বাভাবিক এবং নুমপাইতে প্রত্যাশিত।
ব্যবহারকারী 2357112 মনিকা 20

@ টিমপিডেরিক পারফরম্যান্সের পাশাপাশি হিট এটিও সম্ভবতঃ যে কেউ কোডটি লিখেছিলেন সে নমাই অ্যারে ব্যবহারের লক্ষ্য রাখে। x[x<2]একটি অদ্ভুত অ্যারে প্রদান করবে, যেখানে [0 if i<2 else i for i in x]একটি তালিকা প্রদর্শন করবে। কারণ x[x<2]সূচীকরণ অপারেশন (ডেটা মাস্ক করার ক্ষমতার কারণে স্লাইসিং অপারেশন হিসাবে নম্পি / স্কিপি / প্যান্ডাসে উল্লেখ করা হয়), তবে তালিকা অনুধাবনটি একটি নতুন অবজেক্টের সংজ্ঞা। নম্পপি ইনডেক্সিং
মাইকেল দেলগাদো

45
>>> x = [1,2,3,4,5]
>>> x<2
False
>>> x[False]
1
>>> x[True]
2

বুলটি কেবল একটি পূর্ণসংখ্যায় রূপান্তরিত হয়। সূচক হয় 0 বা 1।


7
আপনি যে উল্লেখ পারে xএবং 2হয় " ধারাবাহিকভাবে কিন্তু ইচ্ছামত আদেশ " এবং ক্রম বিভিন্ন পাইথন বাস্তবায়নের পরিবর্তন হতে পারে।
রোব

4
আমি আরও যুক্ত করব যে এটি কাজ করার একটি চতুর উপায় এবং আমার মতে এড়ানো উচিত। এটি স্পষ্টভাবে করুন - ওপিকে এই প্রশ্নটি জিজ্ঞাসা করতে হয়েছিল তা আমার বক্তব্যকে সমর্থন করে।
kratenko

11
আপনি আরও বিশদ যুক্ত করতে পারেন, কেন x<2 == false?
আইয়া বার্সভ

15
boolকোনও পূর্ণসংখ্যায় রূপান্তরিত হয় না, boolপাইথন- এ একটি পূর্ণসংখ্যা হয়
আন্তি হাপাল

4
শুধু @ অন্য কেউ যে বরাবর আসে জন্য AnttiHaapala বক্তব্য নির্মল bool একটি উপশ্রেণী হয় এর int
পোরগলজম্প

14

আপনার প্রশ্নের মূল কোড শুধুমাত্র পাইথন 2. কাজ করে xএকটি listপাইথন 2 তুলনা x < yহয় Falseযদি yএকটি হয় intEger। এটি কারণ এটি একটি পূর্ণসংখ্যার সাথে তালিকার তুলনা করা মানে তোলে না। তবে পাইথন 2-এ, অপারেশনগুলি তুলনামূলক না হলে, তুলনাটি সিপিথনে ভিত্তিক বর্ণগুলির বর্ণানুক্রমিক ক্রম অনুসারে হয় ; অতিরিক্তভাবে সমস্ত সংখ্যা মিশ্র-প্রকারের তুলনায় প্রথম আসে । সিপিথন 2 এর ডকুমেন্টেশনে এটিও বানান নয়, এবং পাইথন 2 বাস্তবায়ন বিভিন্ন ফলাফল দিতে পারে। এটি [1, 2, 3, 4, 5] < 2মূল্যায়ন করা হয় Falseকারণ 2এটি একটি সংখ্যা এবং এভাবে listসিপিথনের চেয়ে একটি "ছোট" । এই মিশ্র তুলনা শেষ পর্যন্ত ছিলএকটি বৈশিষ্ট্যটিকে খুব অস্পষ্ট বলে মনে করা হয়েছে এবং পাইথন 3.0 এ সরানো হয়েছে।


এখন, ফলাফল <একটি bool; এবং boolএকটি হয় উপশ্রেণী এরint :

>>> isinstance(False, int)
True
>>> isinstance(True, int)
True
>>> False == 0
True
>>> True == 1
True
>>> False + 5
5
>>> True + 5
6

সুতরাং মূলত আপনি তুলনাটি সত্য বা মিথ্যা কিনা তার উপর নির্ভর করে 0 বা 1 উপাদানটি নিচ্ছেন।


যদি আপনি পাইথন 3 এ উপরের কোডটি চেষ্টা করেন তবে পাইথন 3.0 এর পরিবর্তনেরTypeError: unorderable types: list() < int() কারণে আপনি পাবেন :

অর্ডার তুলনা

পাইথন 3.0.০ তুলনামূলক ক্রমানুসারে নিয়মকে সহজ করেছে:

ক্রম তুলনা অপারেটরদের ( <, <=, >=, >) একটি বাড়াতে TypeErrorব্যতিক্রম operands একটি অর্থপূর্ণ প্রাকৃতিক ক্রম হবে না যখন। সুতরাং, এক্সপ্রেশন পছন্দ 1 < '', 0 > Noneবা len <= lenআর বৈধ নয়, আর যেমন None < Noneউত্থাপন TypeErrorফেরার পরিবর্তে False। একটি ছদ্মবেশটি হ'ল ভিন্নজাতীয় তালিকা বাছাই করা আর বোঝা যায় না - সমস্ত উপাদান একে অপরের সাথে তুলনীয় হতে হবে be নোট করুন যে এটি ==এবং !=অপারেটরদের ক্ষেত্রে প্রযোজ্য নয় : বিভিন্ন অতুলনীয় ধরণের জিনিসগুলি সর্বদা একে অপরের সাথে অসম তুলনা করে।


অনেকগুলি ডেটাটাইপ রয়েছে যা তুলনামূলক অপারেটরদের কিছু আলাদা করার জন্য ওভারলোড করে (পান্ডাস, নম্পির অ্যারে থেকে ডেটাফ্রেম)। কোড আছে, আপনি ব্যবহার করছেন সেটি অন্য কিছু করেনি, কারণ ছিল ছিল না , কিন্তু অপারেটর সঙ্গে কিছু অন্যান্য ক্লাসের একটা নিদর্শন নয় একটি মান ফেরত পাঠাতে ওভাররাইড ; এবং এই মানটি তখন (ওরফে / ) বিশেষভাবে পরিচালনা করেxlist<boolx[]__getitem____setitem__


6
+Falseহাই পার্ল, ওহে জাভাস্ক্রিপ্ট, কেমন আছ?
বিড়াল

জাভাস্ক্রিপ্ট, পার্লে @ কেট, এটি মানটিকে সংখ্যা হিসাবে রূপান্তর করে। পাইথনে এটি UNARY_POSITIVEঅপকোডের জন্য যা কল করে__pos__
এন্টি হাপাল

আমি মনে করি আপনি আপনার শেষ বিভাগের __setitem__পরিবর্তে বোঝাতে চেয়েছিলেন __getitem__। এছাড়াও আমি আশা করি আপনি উত্তর দিবেন না যে আমার উত্তরটি আপনার উত্তরের সেই অংশটি দ্বারা অনুপ্রাণিত হয়েছিল।
এমসিফার্ট

না, আমি বোঝাতে চেয়েছিলাম এবং ভাবছিলাম __getitem__যে সমান হতে পারত __setitem__এবং__delitem__
অ্যান্টি হাপাল

9

এর আরও একটি ব্যবহার রয়েছে: কোড গল্ফ। কোড গল্ফ হ'ল প্রোগ্রামগুলি লেখার শিল্প যা সম্ভব যতটা সোর্স কোড বাইটে কিছু সমস্যা সমাধান করে।

return(a,b)[c<d]

মোটামুটি সমান

if c < d:
    return b
else:
    return a

এ এবং বি উভয়ই প্রথম সংস্করণে মূল্যায়ন করা হয় তবে দ্বিতীয় সংস্করণে নয়।

c<dTrueবা মূল্যায়ন False
(a, b)একটি tuple হয়।
একটি টুপলে ইনডেক্সিং একটি তালিকায় সূচকের মতো কাজ করে: (3,5)[1]== 5
Trueসমান 1এবং Falseসমান 0

  1. (a,b)[c<d]
  2. (a,b)[True]
  3. (a,b)[1]
  4. b

বা এর জন্য False:

  1. (a,b)[c<d]
  2. (a,b)[False]
  3. (a,b)[0]
  4. a

কয়েকটি বাইট সংরক্ষণ করার জন্য অজগরকে করতে পারেন এমন অনেক বাজে জিনিসগুলির স্ট্যাক এক্সচেঞ্জ নেটওয়ার্কে একটি ভাল তালিকা রয়েছে। /codegolf/54/tips-for-golfing-in-python

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


6
Code Golf is the art of writing programs: ')
বিড়াল

4
মাইনর nitpick: bool, নয় নিক্ষেপ কোন int- এ, এটা ঠিক নয় এক (অন্যান্য উত্তর দেখুন)
বিড়াল

6

সাধারণভাবে এটা মানে হতে পারে কিছু । এটা ইতিমধ্যেই ছিল ব্যাখ্যা এটা মানে কি যদি xএকটি listবা numpy.ndarrayতবে সাধারণভাবে এটি শুধুমাত্র কিভাবে তুলনা অপারেটরদের (উপর নির্ভর করে <, >, ...) এবং কিভাবে / সেট আইটেম ( [...]-syntax) প্রয়োগ করা হয়।

x.__getitem__(x.__lt__(2))      # this is what x[x < 2] means!
x.__setitem__(x.__lt__(2), 0)   # this is what x[x < 2] = 0 means!

কারণ:

  • x < value সমতুল্য x.__lt__(value)
  • x[value] (মোটামুটি) সমান x.__getitem__(value)
  • x[value] = othervalue(এছাড়াও মোটামুটিভাবে) সমতূল্য x.__setitem__(value, othervalue)

এটি আপনার পছন্দসই কিছু করতে কাস্টমাইজ করা যায় । যেমন একটি উদাহরণ (কিছুটা নমপিস-বুলিয়ান সূচকে নকল করে):

class Test:
    def __init__(self, value):
        self.value = value

    def __lt__(self, other):
        # You could do anything in here. For example create a new list indicating if that 
        # element is less than the other value
        res = [item < other for item in self.value]
        return self.__class__(res)

    def __repr__(self):
        return '{0} ({1})'.format(self.__class__.__name__, self.value)

    def __getitem__(self, item):
        # If you index with an instance of this class use "boolean-indexing"
        if isinstance(item, Test):
            res = self.__class__([i for i, index in zip(self.value, item) if index])
            return res
        # Something else was given just try to use it on the value
        return self.value[item]

    def __setitem__(self, item, value):
        if isinstance(item, Test):
            self.value = [i if not index else value for i, index in zip(self.value, item)]
        else:
            self.value[item] = value

সুতরাং এখন দেখা যাক আপনি এটি ব্যবহার করলে কী হয়:

>>> a = Test([1,2,3])
>>> a
Test ([1, 2, 3])
>>> a < 2  # calls __lt__
Test ([True, False, False])
>>> a[Test([True, False, False])] # calls __getitem__
Test ([1])
>>> a[a < 2] # or short form
Test ([1])

>>> a[a < 2] = 0  # calls __setitem__
>>> a
Test ([0, 2, 3])

লক্ষ্য করুন এটি কেবল একটি সম্ভাবনা। আপনি যা চান তার প্রায়োগিক বাস্তবায়ন করতে আপনি নির্দ্বিধায়।


আমি বলব গ্রহণযোগ্য উত্তরের মতো যৌক্তিকরূপে বোধগম্য আচরণের জন্য সত্যিই কিছু ব্যবহার করা খুব সাধারণ।
পাসক্যালভিকুটেন

@ প্যাসক্লভকুটেন আপনি কি "কিছুর সাথে" বা সাধারণী উত্তরের সাথে একমত নন? আমি মনে করি এটি তৈরির একটি গুরুত্বপূর্ণ বিষয় কারণ পাইথনের বেশিরভাগ যৌক্তিক আচরণ কেবল সম্মেলনের মাধ্যমে by
এমসিফার্ট
আমাদের সাইট ব্যবহার করে, আপনি স্বীকার করেছেন যে আপনি আমাদের কুকি নীতি এবং গোপনীয়তা নীতিটি পড়েছেন এবং বুঝতে পেরেছেন ।
Licensed under cc by-sa 3.0 with attribution required.