Regresi linier dengan fungsi biaya non-simetris?

13

Saya ingin memprediksi beberapa nilai dan saya mencoba untuk mendapatkan beberapa prediksi yang mengoptimalkan antara serendah mungkin, tetapi masih lebih besar dariY(x)Y^(x)Y(x)

cost{Y(x)Y^(x)}>>cost{Y^(x)Y(x)}

Saya pikir regresi linier sederhana harus baik-baik saja. Jadi saya agak tahu bagaimana menerapkan ini secara manual, tapi saya kira saya bukan yang pertama dengan masalah seperti ini. Apakah ada paket / pustaka (lebih disukai python) di luar sana melakukan apa yang ingin saya lakukan? Apa kata kunci yang perlu saya cari?

Bagaimana jika saya tahu fungsi mana Y (x)> Y_0 (x) . Apa cara terbaik untuk menerapkan pembatasan ini?Y0(x)>0Y(x)>Y0(x)

asPlankBridge
sumber
Mungkin, solusi paling sederhana adalah dengan menggunakan bobot yang berbeda, berdasarkan pada apakah prediksi itu positif atau negatif. Aku seharusnya memikirkan itu sebelumnya.
asPlankBridge

Jawaban:

11

Jika saya mengerti Anda dengan benar, Anda ingin berbuat salah di sisi perkiraan terlalu tinggi. Jika demikian, Anda memerlukan fungsi biaya asimetris yang sesuai. Satu kandidat sederhana adalah untuk mengubah kerugian kuadrat:

L:(x,α)x2(sgnx+α)2

di mana adalah parameter yang dapat Anda gunakan untuk menukar penalti perkiraan terlalu rendah terhadap perkiraan terlalu tinggi. Nilai positif dari menghukum penilaian berlebihan, jadi Anda ingin mengatur negative. Dalam python ini terlihat seperti1<α<1ααdef loss(x, a): return x**2 * (numpy.sign(x) + a)**2

Fungsi kerugian untuk dua nilai a

Selanjutnya mari kita menghasilkan beberapa data:

import numpy
x = numpy.arange(-10, 10, 0.1)
y = -0.1*x**2 + x + numpy.sin(x) + 0.1*numpy.random.randn(len(x))

Fungsi sewenang-wenang

Akhirnya, kami akan melakukan regresi kami di tensorflow, pustaka pembelajaran mesin dari Google yang mendukung diferensiasi otomatis (membuat optimasi berbasis gradien dari masalah seperti itu lebih mudah). Saya akan menggunakan contoh ini sebagai titik awal.

import tensorflow as tf

X = tf.placeholder("float") # create symbolic variables
Y = tf.placeholder("float") 

w = tf.Variable(0.0, name="coeff")
b = tf.Variable(0.0, name="offset")
y_model = tf.mul(X, w) + b

cost = tf.pow(y_model-Y, 2) # use sqr error for cost function
def acost(a): return tf.pow(y_model-Y, 2) * tf.pow(tf.sign(y_model-Y) + a, 2)

train_op = tf.train.AdamOptimizer().minimize(cost)
train_op2 = tf.train.AdamOptimizer().minimize(acost(-0.5))

sess = tf.Session()
init = tf.initialize_all_variables()
sess.run(init)

for i in range(100):
    for (xi, yi) in zip(x, y): 
#         sess.run(train_op, feed_dict={X: xi, Y: yi})
        sess.run(train_op2, feed_dict={X: xi, Y: yi})

print(sess.run(w), sess.run(b))

costadalah kesalahan kuadrat biasa, sedangkan acostfungsi kerugian asimetris tersebut di atas.

Jika Anda menggunakan costAnda dapatkan

1,00764 -3,32445

biaya

Jika Anda menggunakan acostAnda dapatkan

1.02604 -1.07742

acost

acostjelas berusaha untuk tidak meremehkan. Saya tidak memeriksa konvergensi, tetapi Anda mendapatkan ide.

Emre
sumber
Terima kasih atas jawaban terinci ini: Satu pertanyaan untuk definisi acostfungsi. Apakah penting Anda menghitung y_model-Ydua kali?
asPlankBridge
Maksud Anda dalam hal kecepatan? Saya tidak tahu; Anda harus mengatur waktu sendiri untuk melihat apakah tensorflow menghindari perhitungan ulang. Tidak masalah jika tidak.
Emre
0

Pilih fungsi kerugian asimetris. Salah satu opsi adalah regresi kuantil (linier tetapi dengan kemiringan berbeda untuk kesalahan positif dan negatif).

Brian Spiering
sumber