在numpy.narray
np.array[map(some_func,x)]
或vectorize(f)(x)
dis_mat = np.zeros([feature_mat.shape[0], feature_mat.shape[0]])
for i in range(feature_mat.shape[0]):
for j in range(i, feature_mat.shape[0]):
dis_mat[i, j] = np.linalg.norm(
feature_mat[i, :] - feature_mat[j, :]
)
dis_mat[j, i] = dis_mat[i, j]
中映射函数的常规方法无法提供索引。
以下代码只是许多应用程序中常见的一个简单示例。
from scipy.spatial.distance import pdist,squareform
dis_mat = squareform(pdist(feature_mat))
有没有办法加快速度?
感谢您的帮助!使用@user2357112评论的函数来加速此代码的最快方法是:
feature_mat
如果feature_mat
很小,那么 @Julien的method也很好,但当import java.util.Scanner;
import java.io.*;
public class practice3
{
public static void main(String[] args) throws IOException
{
int[] array = new int [99];
array = inputData();
for(int i=0; i<array.length; i++)
System.out.printf("%d",array[i]);
}
public static int[] inputData() throws IOException
{
final int MAX= 100;
int[] nums = new int[MAX];
int count = 0;
Scanner kb = new Scanner(System.in);
System.out.print("Enter input file name: ");
String input = kb.nextLine();
File file = new File(input);
if(!file.exists())
{
System.out.println("The file entered is not found");
System.exit(0);
}
Scanner inputFile = new Scanner(file);
while(inputFile.hasNext() && count < nums.length)
{
nums[count] = inputFile.nextInt();
count++;
}
inputFile.close();
return nums;
}
public static void printArray(int[] array, int counter)
{
System.out.println("Original array: ");
System.out.printf("%,12\n", array);
}
}
在2000年时为1000时,它需要近40 GB的内存。< / p>
答案 0 :(得分:16)
SciPy附带了一个专门用于计算您计算的成对距离类型的函数。它是scipy.spatial.distance.pdist
,它以精简格式生成距离,基本上只存储距离矩阵的上三角形,但是您可以将结果转换为带有scipy.spatial.distance.squareform
的方形:
from scipy.spatial.distance import pdist, squareform
distance_matrix = squareform(pdist(feature_mat))
这有利于避免直接矢量化解决方案所需的巨大中间阵列,因此速度更快,适用于更大的输入。但是它失去了an approach that uses algebraic manipulations to have dot
handle the heavy lifting的时间。
pdist
还支持各种备用距离指标,如果您决定要使用欧几里德距离以外的其他指标。
# Manhattan distance!
distance_matrix = squareform(pdist(feature_mat, 'cityblock'))
# Cosine distance!
distance_matrix = squareform(pdist(feature_mat, 'cosine'))
# Correlation distance!
distance_matrix = squareform(pdist(feature_mat, 'correlation'))
# And more! Check out the docs.
答案 1 :(得分:13)
您可以创建新轴并广播:
dis_mat = np.linalg.norm(feature_mat[:,None] - feature_mat, axis=-1)
定时:
feature_mat = np.random.rand(100,200)
def a():
dis_mat = np.zeros([feature_mat.shape[0], feature_mat.shape[0]])
for i in range(feature_mat.shape[0]):
for j in range(i, feature_mat.shape[0]):
dis_mat[i, j] = np.linalg.norm(
feature_mat[i, :] - feature_mat[j, :]
)
dis_mat[j, i] = dis_mat[i, j]
def b():
dis_mat = np.linalg.norm(feature_mat[:,None] - feature_mat, axis=-1)
%timeit a()
100 loops, best of 3: 20.5 ms per loop
%timeit b()
100 loops, best of 3: 11.8 ms per loop
答案 2 :(得分:8)
考虑可以做什么,并在np.dot
矩阵上使用k x k
优化,在小内存位置(kxk):
def c(m):
xy=np.dot(m,m.T) # O(k^3)
x2=y2=(m*m).sum(1) #O(k^2)
d2=np.add.outer(x2,y2)-2*xy #O(k^2)
d2.flat[::len(m)+1]=0 # Rounding issues
return np.sqrt(d2) # O (k^2)
为了比较:
def d(m):
return squareform(pdist(m))
以下是k * k初始矩阵的'时间(it)':
这两个算法是O(k ^ 3),但c(m)
通过np.dot
得到作业的O(k ^ 3)部分,pdist
是线性代数的关键节点,它受益于所有{ {3}}(多核等)。 pdist
只是optimizations中的循环。
这解释了大数组的15倍因子,即使imagename_queue = tf.train.string_input_producer(images, shuffle=False)
labelname_queue = tf.train.string_input_producer([csv_label], shuffle=False)
# print(type(labelname_queue))
image_reader = tf.WholeFileReader()
key_img, raw_img = image_reader.read(imagename_queue)
csv_reader = tf.TextLineReader()
key_txt, raw_txt = csv_reader.read(labelname_queue)
jpg_image = tf.image.decode_jpeg(raw_img)
csv_label = tf.decode_csv(raw_txt, record_defaults=[[0]])
jpg_image = tf.reduce_mean(jpg_image, axis=2)
jpg_image = tf.reshape(jpg_image, [W_img, H_img, 1])
仅通过计算一半的术语来利用矩阵的对称性。
答案 3 :(得分:2)
我想避免混用NumPy和for
循环的一种方法是使用允许替换的版本of this index creator创建索引数组:
import numpy as np
from itertools import product, chain
from scipy.special import comb
def comb_index(n, k):
count = comb(n, k, exact=True, repetition=True)
index = np.fromiter(chain.from_iterable(product(range(n), repeat=k)),
int, count=count*k)
return index.reshape(-1, k)
然后,我们简单地获取每个数组对,计算它们之间的差异,重新生成结果数组,并采用数组中每一行的范数:
reshape_mat = np.diff(feature_mat[comb_index(feature_mat.shape[0], 2), :], axis=1).reshape(-1, feature_mat.shape[1])
dis_list = np.linalg.norm(reshape_mat, axis=-1)
请注意,dis_list
只是所有n*(n+1)/2
可能norms
的列表。这与他提供的feature_mat
的其他答案的速度接近,并且在比较我们最大部分的字节大小时,
(feature_mat[:,None] - feature_mat).nbytes == 16000000
,而
np.diff(feature_mat[comb_index(feature_mat.shape[0], 2), :], axis=1).reshape(-1, feature_mat.shape[1]).nbytes == 8080000
对于大多数投入,我只使用了一半的存储:仍然不是最理想的,但是边际改善。
答案 4 :(得分:2)
基于func initiateCentralManager(){
manager = CBCentralManager(delegate: self, queue: nil, options: [CBCentralManagerOptionRestoreIdentifierKey : "MyBLECurrentState"])
}
func centralManagerDidUpdateState(_ central: CBCentralManager){
print("Received CBCentralManager state")
peripheralArray.removeAll()
if central.state == .poweredOn {
print("poweredOn")
} else if central.state == .poweredOff {
print("poweredOff")
}
}
,如果你真的想用纯NumPy做这件事:
np.triu_indices
这种方法相对于广播的好处是你可以用块来做:
s = feature_mat.shape[0]
i, j = np.triu_indices(s, 1) # All possible combinations of indices
dist_mat = np.empty((s, s)) # Don't waste time filling with zeros
np.einsum('ii->i', dist_mat)[:] = 0 # When you can just fill the diagonal
dist_mat[i, j] = dist_mat[j, i] = np.linalg.norm(feature_mat[i] - feature_mat[j], axis=-1)
# Vectorized version of your original process
答案 5 :(得分:-1)
让我们从函数的重写开始:
dist(mat, i, j):
return np.linalg.norm(mat[i, :] - mat[j, :])
size = feature_mat.shape[0]
for i in range(size):
for j in range(size):
dis_mat[i, j] = dist(feature_mat, i, j)
这可以用(稍微更多)矢量化形式重写为:
v = [dist(feature_map, i, j) for i in range(size) for j in range(size)]
dist_mat = np.array(v).reshape(size, size)
请注意,我们仍然依赖于Python而不是NumPy进行某些计算,但它是向量化的一步。还要注意dist(i, j)
是对称的,因此我们可以进一步减少大约一半的计算量。也许正在考虑:
v = [dist(feature_map, i, j) for i in range(size) for j in range(i + 1)]
现在棘手的一点是将这些计算值分配给dist_mat
中的正确元素。
此效果的速度取决于计算dist(i, j)
的成本。对于较小的feature_mat
,重新计算的成本不足以担心这一点。但是对于大型矩阵,你绝对不想重新计算。