1

私は次のようなアルゴリズムを持っています:

  • 2つの入力(x、y)を取ります。ここで、xとyは、2つの独立したポアソン分布の「ラムダ」変数です(http://en.wikipedia.org/wiki/Poisson_distribution#Definition
  • xとyのそれぞれのポアソンベクトルを計算します。
  • 2つのポアソンベクトルの行列積を計算します
  • [sum(upper_quadrant)、sum(lower_quadrant)、sum(diagonal)]を返します

それで:

import math, random

def poisson(m, n):
    p=math.exp(-m)
    r=[p]
    for i in range(1, n):
        p*=m/float(i)
        r.append(p)
    return r

def simulate(mx, my, n):
    r=[0.0 for i in range(3)]
    px, py = (poisson(mx, n), 
              poisson(my, n))
    for i in range(n):
        for j in range(n):
            if i > j:
                k=0
            elif i < j:
                k=1
            else:
                k=2
            r[k]+=px[i]*py[j]
    return r

次に、特定の出力セットを指定して、xとyを解く必要があります。次のソルバー関数を一緒にハッキングしました。

def solve(p, n, generations, decay, tolerance):
    def rms_error(X, Y):
        return (sum([(x-y)**2 
                     for x, y in zip(X, Y)])/float(len(X)))**0.5
    def calc_error(x, y, n, target):
        guess=simulate(x, y, n)
        return rms_error(target, guess)    
    q=[0, 0]
    err=calc_error(math.exp(q[0]), math.exp(q[1]), n, p)
    bestq, besterr = q, err
    for i in range(generations):
        if besterr < tolerance:
            break
        q=list(bestq)
        if random.random() < 0.5:
            j=0
        else:
            j=1
        fac=((generations-i+1)/float(generations))**decay
        q[j]+=random.gauss(0, 1)*fac
        err=calc_error(math.exp(q[0]), math.exp(q[1]), n, p)
        if err < besterr:
            bestq, besterr = q, err
            # print (i, bestq, besterr)
    q, err = [math.exp(q) for q in bestq], besterr
    return (i, q, err)

これは機能しますが、あまり最適化されていない応答を返すために比較的多くの試行が必要なようです。

if __name__=="__main__":
    p, n = [0.5, 0.2, 0.3], 10
    q, err = solve_match_odds(p, n, 
                              generations=1000,
                              decay=2,
                              tolerance=1e-5)
    print q
    print simulate_match_odds(q[0], q[1], n)
    print (i, err)

と:

justin@justin-ThinkPad-X220:~/work/$ python solve.py 
[0.5, 0.2, 0.3]
[0.5000246335218251, 0.20006624338256798, 0.29990837191131686]
(999, 6.680993630511076e-05)
justin@justin-ThinkPad-X220:~/work/$

私はCS専攻ではないので、ここで検索に関するあらゆる文献を見逃していると感じています。誰かがこのような2次元空間で変数を検索するためのより良い方法を提案できますか?

ありがとう。

4

1 に答える 1

0

これを解決するには、 scipy.optimizeライブラリを使用できます。

import math, random

def poisson(m, n):
    p=math.exp(-m)
    r=[p]
    for i in range(1, n):
        p*=m/float(i)
        r.append(p)
    return r

def simulate(mx, my, n):
    r=[0.0 for i in range(3)]
    px, py = (poisson(mx, n), 
              poisson(my, n))
    for i in range(n):
        for j in range(n):
            if i > j:
                k=0
            elif i < j:
                k=1
            else:
                k=2
            r[k]+=px[i]*py[j]
    return r

from scipy import optimize

Target, N = [0.5, 0.2, 0.3], 10

def error(p, target, n):
    r = simulate(p[0], p[1], n)
    return np.sum(np.subtract(target, r)**2)

r = optimize.fmin(error, (0, 0), args=(Target, N))
print simulate(r[0], r[1], n)

出力:

Optimization terminated successfully.
         Current function value: 0.000000
         Iterations: 67
         Function evaluations: 125
[0.49999812501285623, 0.20000418001288445, 0.2999969464616799]
于 2013-03-21T07:56:27.210 に答える