有没有一种很好的方法可以在不使用磁盘的情况下在两个python子进程之间传递大量数据?这是我希望完成的动画示例:
import sys, subprocess, numpy
cmdString = """
import sys, numpy
done = False
while not done:
cmd = raw_input()
if cmd == 'done':
done = True
elif cmd == 'data':
##Fake data. In real life, get data from hardware.
data = numpy.zeros(1000000, dtype=numpy.uint8)
data.dump('data.pkl')
sys.stdout.write('data.pkl' + '\\n')
sys.stdout.flush()"""
proc = subprocess.Popen( #python vs. pythonw on Windows?
[sys.executable, '-c %s'%cmdString],
stdin=subprocess.PIPE,
stdout=subprocess.PIPE,
stderr=subprocess.PIPE)
for i in range(3):
proc.stdin.write('data\n')
print proc.stdout.readline().rstrip()
a = numpy.load('data.pkl')
print a.shape
proc.stdin.write('done\n')
Run Code Online (Sandbox Code Playgroud)
这将创建一个子进程,该子进程生成numpy数组并将数组保存到磁盘.然后父进程从磁盘加载数组.有用!
问题是,我们的硬件可以生成比磁盘可读/写快10倍的数据.有没有办法将数据从一个python进程传输到另一个纯内存中,甚至可能没有复制数据?我可以做一些像传递参考的东西吗?
我第一次尝试纯粹在内存中传输数据是非常糟糕的:
import …Run Code Online (Sandbox Code Playgroud) 与这个答案类似,我有一对3D numpy数组,a并且b,我想按照b值的值对条目进行排序a.与此答案不同,我只想沿阵列的一个轴排序.
我天真地阅读了numpy.argsort()文档:
Returns
-------
index_array : ndarray, int
Array of indices that sort `a` along the specified axis.
In other words, ``a[index_array]`` yields a sorted `a`.
Run Code Online (Sandbox Code Playgroud)
让我相信我可以使用以下代码进行排序:
import numpy
a = numpy.zeros((3, 3, 3))
a += numpy.array((1, 3, 2)).reshape((3, 1, 1))
print "a"
print a
"""
[[[ 1. 1. 1.]
[ 1. 1. 1.]
[ 1. 1. 1.]]
[[ 3. 3. 3.]
[ 3. 3. …Run Code Online (Sandbox Code Playgroud) 如果我从终端运行以下代码,我会在终端中收到有用的错误消息:
import Tkinter as tk
master = tk.Tk()
def callback():
raise UserWarning("Exception!")
b = tk.Button(master, text="This will raise an exception", command=callback)
b.pack()
tk.mainloop()
Run Code Online (Sandbox Code Playgroud)
但是,如果我在没有终端的情况下运行它(例如,通过双击图标),则会禁止显示错误消息.
在我真实的,更复杂的Tkinter应用程序中,我喜欢GUI有点防撞击.我不喜欢我的用户很难给我有用的反馈来解决导致的意外行为.
我该怎么处理?有没有一种标准方法可以在Tkinter应用程序中公开回溯或stderror或诸如此类的东西?我正在寻找比尝试/除了各处更优雅的东西.
编辑:Jochen Ritzel给出了一个很好的答案,弹出一个警告框,并提到将它附加到一个班级.只是为了明确这一点:
import Tkinter as tk
import traceback, tkMessageBox
class App:
def __init__(self, master):
master.report_callback_exception = self.report_callback_exception
self.frame = tk.Frame(master)
self.frame.pack()
b = tk.Button(
self.frame, text="This will cause an exception",
command=self.cause_exception)
b.pack()
def cause_exception(self):
a = []
a.a = 0 #A traceback makes this easy to catch and fix
def report_callback_exception(self, *args):
err = …Run Code Online (Sandbox Code Playgroud) 当我尝试将ctypes数组用作numpy数组时,我收到以下警告消息:
Python 2.7.1 (r271:86832, Nov 27 2010, 18:30:46) [MSC v.1500 32 bit (Intel)] on
win32
Type "help", "copyright", "credits" or "license" for more information.
>>> import ctypes, numpy
>>> TenByteBuffer = ctypes.c_ubyte * 10
>>> a = TenByteBuffer()
>>> b = numpy.ctypeslib.as_array(a)
C:\Python27\lib\site-packages\numpy\ctypeslib.py:402: RuntimeWarning: Item size
computed from the PEP 3118 buffer format string does not match the actual item s
ize.
return array(obj, copy=False)
>>> b
array([0, 0, 0, 0, 0, 0, 0, 0, 0, 0], dtype=uint8)
Run Code Online (Sandbox Code Playgroud)
但是代码似乎正在起作用.忽略这个警告是不是一个坏主意?
背景:我正在调用一个实时生成数据的C …
我经常将16位灰度图像数据转换为8位图像数据以供显示.调整最小和最大显示强度以突出显示图像的"有趣"部分几乎总是有用的.
下面的代码粗略地做了我想要的,但是它很丑陋且效率低下,并且制作了许多图像数据的中间副本.如何以最小的内存占用和处理时间实现相同的结果?
import numpy
image_data = numpy.random.randint( #Realistic images would be much larger
low=100, high=14000, size=(1, 5, 5)).astype(numpy.uint16)
display_min = 1000
display_max = 10000.0
print(image_data)
threshold_image = ((image_data.astype(float) - display_min) *
(image_data > display_min))
print(threshold_image)
scaled_image = (threshold_image * (255. / (display_max - display_min)))
scaled_image[scaled_image > 255] = 255
print(scaled_image)
display_this_image = scaled_image.astype(numpy.uint8)
print(display_this_image)
Run Code Online (Sandbox Code Playgroud) 我知道通过Tkinter将MxNx3 numpy数组显示为RGB图像的配方,但我的配方在此过程中制作了几个数组副本:
a = np.random.randint(low=255, size=(100, 100, 3), dtype=np.uint8) # Original
ppm_header = b'P6\n%i %i\n255\n'%(a.shape[0], a.shape[1])
a_bytes = a.tobytes() # First copy
ppm_bytes = ppm_header + a_bytes # Second copy https://en.wikipedia.org/wiki/Netpbm_format
root = tk.Tk()
img = tk.PhotoImage(data=ppm_bytes) # Third and fourth copies?
canvas = tk.Canvas(root, width=a.shape[0], height=a.shape[1])
canvas.pack()
canvas.create_image(0, 0, anchor=tk.NW, image=img) # Fifth copy?
root.mainloop()
Run Code Online (Sandbox Code Playgroud)
如何以最少的份数获得相同的结果?
理想情况下,我会创建一个numpy数组,它是Tkinter PhotoImage对象使用的相同字节的视图,有效地为我提供了一个PhotoImage可变的像素值,并使更新Tkinter显示更便宜和快速.我不知道如何从Tkinter中提取这个指针.
也许有一种通过ctypes的方式,正如这里暗示的那样?
这个PhotoImage.put()方法似乎很慢,但也许我错了,那是一条前进的道路?
我尝试制作一个bytearray()包含ppm标题和图像像素值,然后使用numpy.frombuffer()查看图像像素值作为一个numpy数组,但我认为PhotoImage构造函数想要一个bytes()对象,而不是一个bytearray()对象,而且我认为Tkinter复制字节的它data …
我想'剪切'一个numpy阵列.我不确定我是否正确使用"剪切"一词; 通过剪切,我的意思是:
将第一列
移动0个位置将第二列
移动1个位置将第三个列移动2个位置
等...
所以这个数组:
array([[11, 12, 13],
[17, 18, 19],
[35, 36, 37]])
Run Code Online (Sandbox Code Playgroud)
会变成这个数组:
array([[11, 36, 19],
[17, 12, 37],
[35, 18, 13]])
Run Code Online (Sandbox Code Playgroud)
或类似这样的数组:
array([[11, 0, 0],
[17, 12, 0],
[35, 18, 13]])
Run Code Online (Sandbox Code Playgroud)
取决于我们如何处理边缘.我不太关注边缘行为.
这是我尝试执行此操作的函数:
import numpy
def shear(a, strength=1, shift_axis=0, increase_axis=1, edges='clip'):
strength = int(strength)
shift_axis = int(shift_axis)
increase_axis = int(increase_axis)
if shift_axis == increase_axis:
raise UserWarning("Shear can't shift in the direction it increases")
temp = numpy.zeros(a.shape, dtype=int)
indices = []
for d, num in enumerate(a.shape): …Run Code Online (Sandbox Code Playgroud) 帮助我的代码更快:我的python代码需要生成一个落在边界矩形内的2D点阵.我把一些生成这个点阵的代码(如下所示)拼凑在了一起.但是,这个函数被多次调用,并且已经成为我应用程序中的一个严重瓶颈.
我确信有更快的方法可以做到这一点,可能涉及numpy数组而不是列表.有什么建议可以更快,更优雅地做到这一点吗?
功能描述:我有两个2D矢量,v1和v2.这些矢量定义了一个晶格.在我的例子中,我的矢量定义了一个几乎但不完全是六边形的格子.我想在这个晶格上生成一些边界矩形中的所有2D点的集合.在我的例子中,矩形的一个角是(0,0),其他角是正坐标.
示例:如果我的边界矩形的远角位于(3,3),并且我的点阵向量是:
v1 = (1.2, 0.1)
v2 = (0.2, 1.1)
Run Code Online (Sandbox Code Playgroud)
我希望我的函数返回点:
(1.2, 0.1) #v1
(2.4, 0.2) #2*v1
(0.2, 1.1) #v2
(0.4, 2.2) #2*v2
(1.4, 1.2) #v1 + v2
(2.6, 1.3) #2*v1 + v2
(1.6, 2.3) #v1 + 2*v2
(2.8, 2.4) #2*v1 + 2*v2
Run Code Online (Sandbox Code Playgroud)
我不关心边缘情况; 例如,函数返回(0,0)无关紧要.
我目前正在做的缓慢的方式:
import numpy, pylab
def generate_lattice( #Help me speed up this function, please!
image_shape, lattice_vectors, center_pix='image', edge_buffer=2):
##Preprocessing. Not much of a bottleneck:
if center_pix == 'image': …Run Code Online (Sandbox Code Playgroud) 我正在使用python的pyglet模块(Windows上的python 3).当我引用pyglet.image中的任何类时,python的CPU使用率会跳起来并且在我退出python之前不会下降.例如:
Microsoft Windows [Version 6.1.7601]
Copyright (c) 2009 Microsoft Corporation. All rights reserved.
C:\Anaconda3>python.exe
Python 3.4.3 |Anaconda 2.3.0 (64-bit)| (default, Mar 6 2015, 12:06:10) [MSC v.1
600 64 bit (AMD64)] on win32
Type "help", "copyright", "credits" or "license" for more information.
>>> import pyglet #No problem!
>>> pyglet.image.ImageData #Heavy CPU load until I exit python
<class 'pyglet.image.ImageData'>
Run Code Online (Sandbox Code Playgroud)
这是预期的行为吗?为什么提这个类(甚至没有实例化它)会导致如此高的CPU负载?
我测试的系统:
带有Anaconda python 3.4.3的Windows 7桌面和通过'pip install pyglet'安装的pyglet:高CPU使用率(我的问题)
与Anaconda python 3.4.3相同的Win7桌面,但通过'pip install hg + https://bitbucket.org/pyglet/pyglet ' 安装了pyglet :高CPU使用率.
来自python.org的python …
编辑:根据JF Sebastian的建议,我可以更简单地得到同样的错误:
Python 2.6.4 (r264:75708, Oct 26 2009, 08:23:19) [MSC v.1500 32 bit (Intel)]
Type "copyright", "credits" or "license" for more information.
IPython 0.10 -- An enhanced Interactive Python.
? -> Introduction and overview of IPython's features.
%quickref -> Quick reference.
help -> Python's own help system.
object? -> Details about 'object'. ?object also works, ?? prints more.
Welcome to pylab, a matplotlib-based Python environment.
For more information, type 'help(pylab)'.
In [1]: open(r'c:\test.bin', 'wb').write('a'*67076095)
In [2]: open(r'c:\test.bin', 'wb').write('a'*67076096)
In [3]: …Run Code Online (Sandbox Code Playgroud)