আমি একটি অ্যারে প্রদত্ত শর্তের উপাদানগুলি কীভাবে নির্বাচন করব?


156

আমি একটি numpy অ্যারে আছে ধরুন x = [5, 2, 3, 1, 4, 5], y = ['f', 'o', 'o', 'b', 'a', 'r']। আমি যে yউপাদানগুলি x1 এর চেয়ে বেশি এবং 5 এর চেয়ে কম এর সাথে সম্পর্কিত উপাদানগুলিকে নির্বাচন করতে চাই ।

আমি চেষ্টা করেছিলাম

x = array([5, 2, 3, 1, 4, 5])
y = array(['f','o','o','b','a','r'])
output = y[x > 1 & x < 5] # desired output is ['o','o','a']

কিন্তু এটি কাজ করে না। আমি এই কিভাবে করব?

উত্তর:


220

আপনি প্রথম বন্ধনী যুক্ত করলে আপনার অভিব্যক্তি কাজ করে:

>>> y[(1 < x) & (x < 5)]
array(['o', 'o', 'a'], 
      dtype='|S1')

1
এটি দুর্দান্ত .. vecMask = 1 <x ভেকমাস্ক = (মিথ্যা, সত্য, ...) এর মতো একটি ভেক্টর মাস্ক উত্পন্ন করে, যা কেবল অন্য ভেক্টর মাস্কের সাথে একত্রিত হতে পারে। প্রতিটি উপাদান হ'ল উত্স ভেক্টরের উপাদানগুলি নেওয়ার শর্ত (সত্য) বা না (মিথ্যা)। এটি পুরো সংস্করণ numpy.extract (vecMask, vecSrc), বা numpy.where (vecMask, vecSrc, vecSrc2) এর সাথেও ব্যবহার করা যেতে পারে।
মাস্টারকন্ট্রোল প্রোগ্রাম

6
@ জেনি ইউ জিন: এটি প্রাধান্যের কারণে ঘটে। (বিটওয়াইজ) &এর চেয়ে বেশি অগ্রাধিকার রয়েছে <এবং এর >পরিবর্তে (যৌক্তিক) চেয়ে বেশি অগ্রাধিকার রয়েছে andx > 1 and x < 5প্রথমে বৈষম্যগুলি এবং তারপরে যৌক্তিক সংমিশ্রণটি বের করে দেয়; x > 1 & x < 5এর বিটওয়াইস সংমিশ্রণ 1এবং (এর মানগুলি) মূল্যায়ন করে x, তারপরে অসম্পূর্ণতাগুলি। (x > 1) & (x < 5)অসমতার জন্য প্রথমে মূল্যায়ন করতে বাধ্য করে, সুতরাং সমস্ত ক্রিয়াকলাপটি নিয়মিত ক্রমে ঘটে এবং ফলাফলগুলি সমস্ত সংজ্ঞায়িত হয়। ডক্স এখানে দেখুন।
ক্যালাভিচি

@ রু 111 এটি পাইথন ৩.6-তেও কাজ করে (এটি কাজ বন্ধ করার কোনও কারণ নেই)।
jfs

আমি পেয়েছি "ভ্যালুআররির: একাধিক উপাদান সহ একটি অ্যারের সত্য মান দ্বিধাগ্রস্ত। A.any () বা a.all ()"
রু 111

@ রু 111 আপনার লিখতে হবে (0 < x) & (x < 10)(উত্তরে উত্তর হিসাবে) এর পরিবর্তে 0 < x < 10কোনও পাইথন সংস্করণে আঙ্কুল অ্যারেগুলির জন্য কাজ করে না।
jfs

34

আইএমও ওপি আসলে np.bitwise_and()(ওরফে &) চায় না তবে প্রকৃতপক্ষে চায় np.logical_and()কারণ তারা লজিক্যাল মানগুলির তুলনা করছে যেমন Trueএবং False- পার্থক্যটি দেখতে লজিক্যাল বনাম বিটওয়াসে এই এসও পোস্টটি দেখুন।

>>> x = array([5, 2, 3, 1, 4, 5])
>>> y = array(['f','o','o','b','a','r'])
>>> output = y[np.logical_and(x > 1, x < 5)] # desired output is ['o','o','a']
>>> output
array(['o', 'o', 'a'],
      dtype='|S1')

এবং এটি করার সমতুল্য উপায়টি যুক্তিটি যথাযথভাবে np.all()সেট করা সহ axis

>>> output = y[np.all([x > 1, x < 5], axis=0)] # desired output is ['o','o','a']
>>> output
array(['o', 'o', 'a'],
      dtype='|S1')

সংখ্যা দ্বারা:

>>> %timeit (a < b) & (b < c)
The slowest run took 32.97 times longer than the fastest. This could mean that an intermediate result is being cached.
100000 loops, best of 3: 1.15 µs per loop

>>> %timeit np.logical_and(a < b, b < c)
The slowest run took 32.59 times longer than the fastest. This could mean that an intermediate result is being cached.
1000000 loops, best of 3: 1.17 µs per loop

>>> %timeit np.all([a < b, b < c], 0)
The slowest run took 67.47 times longer than the fastest. This could mean that an intermediate result is being cached.
100000 loops, best of 3: 5.06 µs per loop

সুতরাং ব্যবহার np.all()করা ধীর, &এবং logical_andপ্রায় একই।


7
যা মূল্যায়ন করা হয় সে সম্পর্কে আপনি কীভাবে বক্তব্য রাখেন সে সম্পর্কে আপনাকে একটু সতর্ক হওয়া দরকার। উদাহরণস্বরূপ, মধ্যে output = y[np.logical_and(x > 1, x < 5)], x < 5 হয় মূল্যায়ন (সম্ভবত একটি বিরাট অ্যারে তৈরি), যদিও এটি দ্বিতীয় যুক্তি, কারণ যে মূল্যায়ন ফাংশনের বাইরে ঘটে। আইডাব্লু, logical_andইতিমধ্যে দুটি মূল্যায়ন যুক্তি পাস হয়। এটি সাধারণ ক্ষেত্রে থেকে আলাদা a and b, যার মধ্যে সত্যবাদী bহলে মূল্যায়ন করা হয় না a
ডিএসএম

15
বুলিয়ান অ্যারেগুলির জন্য বিটওয়াইজ_এন্ড () এবং লজিক্যাল_এন্ড () এর মধ্যে কোনও পার্থক্য নেই
jfs

21

@ জেএফ সেবাস্তিয়ান এবং @ মার্ক মিকোফস্কির জবাবগুলিতে একটি বিশদ যুক্ত করুন:
যদি কেউ সূচকগুলি (অ্যারের প্রকৃত মানগুলির চেয়ে) পেতে চান তবে নিম্নলিখিত কোডটি করবে:

একাধিক (সমস্ত) শর্ত সন্তুষ্ট করার জন্য:

select_indices = np.where( np.logical_and( x > 1, x < 5) )[0] #   1 < x <5

একাধিক (বা) শর্ত পূরণ করার জন্য:

select_indices = np.where( np.logical_or( x < 1, x > 5 ) )[0] # x <1 or x >5

2
মনে রাখবেন যে, numpy.where শুধু সূচকের একটি অ্যারের আসতে হবে না, কিন্তু এর পরিবর্তে একটি tuple ফিরে আসবে (condition.nonzero আউটপুট ()) অ্যারে ধারণকারী - এই ক্ষেত্রে, (the array of indices you want,), তাই আপনার প্রয়োজন হবে select_indices = np.where(...)[0]ফলাফলের আপনি চান পেতে এবং আশা
ক্যালাভিচি

5

আমি এই np.vectorizeধরনের কাজের জন্য ব্যবহার করতে চাই । নিম্নোক্ত বিবেচনা কর:

>>> # Arrays
>>> x = np.array([5, 2, 3, 1, 4, 5])
>>> y = np.array(['f','o','o','b','a','r'])

>>> # Function containing the constraints
>>> func = np.vectorize(lambda t: t>1 and t<5)

>>> # Call function on x
>>> y[func(x)]
>>> array(['o', 'o', 'a'], dtype='<U1')

সুবিধাটি হ'ল আপনি ভেক্টরাইজড ফাংশনে আরও অনেক ধরণের সীমাবদ্ধতা যুক্ত করতে পারেন।

আশা করি এটা সাহায্য করবে.


1
এটি NumPy ইনডেক্সিং করার ভাল উপায় নয় (এটি খুব ধীর হবে)।
অ্যালেক্স রিলি

1

আসলে আমি এটি এইভাবে করব:

এল 1 হ'ল সন্তোষজনক শর্ত 1 এর উপাদানগুলির সূচক তালিকা; (সম্ভবত আপনি ব্যবহার করতে পারেন somelist.index(condition1)বা np.where(condition1)এল 1 পেতে পারেন ))

একইভাবে, আপনি এল 2 পান, সন্তুষ্ট শর্ত 2 এর উপাদানগুলির একটি তালিকা;

তারপরে আপনি ছেদটি ব্যবহার করে খুঁজে পাবেন intersect(L1,L2)

আপনি যদি একাধিক শর্ত পূরণ করার জন্য একাধিক তালিকার ছেদও খুঁজে পেতে পারেন।

তারপরে আপনি অন্য কোনও অ্যারেতে সূচক প্রয়োগ করতে পারেন, উদাহরণস্বরূপ, এক্স।


0

2 ডি অ্যারেগুলির জন্য, আপনি এটি করতে পারেন। শর্তটি ব্যবহার করে একটি 2D মাস্ক তৈরি করুন। অ্যারের উপর নির্ভর করে কন্ডিশন মাস্কটি ইনট বা ফ্লোটে টাইপ করুন এবং এটি মূল অ্যারে দিয়ে গুণ করুন।

In [8]: arr
Out[8]: 
array([[ 1.,  2.,  3.,  4.,  5.],
       [ 6.,  7.,  8.,  9., 10.]])

In [9]: arr*(arr % 2 == 0).astype(np.int) 
Out[9]: 
array([[ 0.,  2.,  0.,  4.,  0.],
       [ 6.,  0.,  8.,  0., 10.]])
আমাদের সাইট ব্যবহার করে, আপনি স্বীকার করেছেন যে আপনি আমাদের কুকি নীতি এবং গোপনীয়তা নীতিটি পড়েছেন এবং বুঝতে পেরেছেন ।
Licensed under cc by-sa 3.0 with attribution required.