0

python Numpy vectorization を使用して、この演習 4.5 を 2 ページで解決するにはどうすればよいですか?

ダウンロードへのリンク:

https://dl.dropbox.com/u/92795325/Python%20Scripting%20for%20Computational%20Scien%20-%20H.P.%20%20Langtangen.pdf

Python ループでこれを試しましたが、ベクトル化バージョンが必要です。

from numpy import *
import time

def fun1(x):
       return 2*x+1

def integ(a,b,n):
       t0 = time.time()
       h = (b-a)/n
       a1 = (h/2)*fun1(a)
       b1 = (h/2)*fun1(b)
       c1 = 0
       for i in range(1,n,1):
              c1 = fun1((a+i*h))+c1
       t1 = time.time()
       return a1+b1+h*c1, t1-t0
4

1 に答える 1

0

を使用して「ベクトル化」numpyするには、次のような明示的なループを実行する代わりに、

for i in range(1, n):
    c = c + f(i)

次に、代わりにinumpy 配列を作成し、単純にその合計を取る必要があります。

i = np.arange(1,n)
c = i.sum()

numpy は自動的にベクトル化を行います。これが高速である理由は、さまざまな理由から、普通の python ループよりも最適化された方法で numpy ループが実行されるためです。一般的に言えば、ループ/配列が長いほど有利です。実装された台形積分は次のとおりです。

import numpy as np

def f1(x):
    return 2*x + 1

# Here's your original function modified just a little bit:
def integ(f,a,b,n):
    h = (b-a)/n
    a1 = (h/2)*f(a)
    b1 = (h/2)*f(b)
    c1 = 0
    for i in range(1,n,1):
        c1 = f((a+i*h))+c1
    return a1 + b1 + h*c1

# Here's the 'vectorized' function:
def vinteg(f, a, b, n):
    h = (b-a) / n
    ab = 0.5 * h * (f(a)+f(b)) #only divide h/2 once

    # use numpy to make `i` a 1d array:
    i = np.arange(1, n) 
    # then, passing a numpy array to `f()` means that `f` returns an array
    c = f(a + h*i) # now c is a numpy array

    return ab + c.sum() # ab + np.sum(c) is equivalent

ここでは、使用するよりもタイミングを簡単にするために、名前を付けたものをセッションtmp.pyにインポートします。ipythontime.time

import trap
f = trap.f1
a = 0
b = 100
n = 1000

timeit trap.integ(f, a, b, n)
#1000 loops, best of 3: 378 us per loop

timeit trap.vinteg(f, a, b, n)
#10000 loops, best of 3: 51.6 us per loop

うわー、7倍速い。

それがより小さなものに役立つかどうかを確認してくださいn

n = 10

timeit trap.integ(f, a, b, n)
#100000 loops, best of 3: 6 us per loop

timeit trap.vinteg(f, a, b, n)
#10000 loops, best of 3: 43.4 us per loop

いいえ、小さなループの場合ははるかに遅くなります! 非常に大きいのはnどうですか?

n = 10000

timeit trap.integ(f, a, b, n)
#100 loops, best of 3: 3.69 ms per loop

timeit trap.vinteg(f, a, b, n)
#10000 loops, best of 3: 111 us per loop

30倍速い!

于 2013-04-06T22:20:09.890 に答える