2014-07-08 21 views
6

Tôi có một mảng có sẵn và một danh sách chứa một số đối tượng lát cắt (có chứa (start, end) tuple). Tôi đang tìm cách để loại bỏ các vị trí đối tượng slice từ mảng ban đầu và nhận được một mảng thứ hai với các giá trị còn lại.Xóa nhiều lát từ một mảng có nhiều mảng

Toy dụ:

myarray = np.arange(20) 

array([ 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 
     17, 18, 19]) 

mylist=(slice(2,4),slice(15,19)) 

làm điều gì đó và kết quả nên

array([0, 1, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14]) 

Mảng có thể được trong một vài trăm ngàn lớn, danh sách các đối tượng slice có thể chứa vài ngàn yếu tố và Tôi cần phải chạy các hoạt động thường xuyên, vì vậy tốc độ là hơi quan trọng.

Xóa hàng loạt không lấy danh sách các lát mà tôi có thể thấy?

Hiện tại tôi đang tạo danh sách đối tượng slice và cắt nó, nhưng tạo ra phần bổ sung là một quá trình hơi khó xử khi tôi sắp xếp danh sách slice của mình sau đó lặp qua nó, tạo các đối tượng slice bổ sung nếu cần. Tôi hy vọng có một cách tao nhã hơn tôi đã không hình dung!

Trả lời

1

Bạn có thể sử dụng set() để xác định vị trí sẽ được lưu giữ và np.take() để có được những giá trị tương ứng, làm một cái gì đó như:

ind = np.indices(myarray.shape)[0] 
rm = np.hstack([ind[i] for i in mylist]) 

ans = np.take(myarray, sorted(set(ind)-set(rm))) 

Lưu ý rằng np.hstack() được sử dụng để có được một mảng duy nhất với tất cả các chỉ số đó sẽ bị xóa. Điều này mất khoảng một nửa thời gian của giải pháp @ HYRY.

+1

Điều đó làm việc tuyệt vời, chúc mừng! – anordell

1

Tôi không thể nghĩ ra cách để tham gia các lát sạch sẽ; tuy nhiên, tôi nghĩ việc sử dụng composite là cách để đi. Có lẽ thử một cái gì đó như thế này:

import numpy as np 

# Create test data 
n_data = 1000000 
n_slices = 10000 

data = np.arange(n_data) 
slices = [] 
for i in range(n_slices): 
    r = np.random.randint(n_data-1000) 
    slices.append(slice(r,r + np.random.randint(1000))) 

# Remove slices 
keep_mask = np.ones_like(data, dtype=bool) 
for slice in slices: keep_mask[slice] = False 
data = data[keep_mask] # or np.take, etc. 
1

Bạn có thể sử dụng np.r_[] tham gia các lát vào một mảng:

myarray = np.arange(20) 
mylist=(slice(2, 4),slice(15, 19)) 
np.delete(myarray, np.r_[tuple(mylist)]) 

đầu ra:

array([ 0, 1, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 19]) 

Nhưng tôi nghĩ rằng nó không phải là rất nhanh.

Các vấn đề liên quan