Help us understand the problem. What is going on with this article?

パーセプトロンを使って論理演算を実行する

はじめに

パーセプトロンとは何か、を理解することが目標です.

パーセプトロンとは

複数の信号を入力として受け取り、ひとつの信号を出力します. 出力信号は0または1の二値をとるものです.

2020-01-24 (3).png

x1,x2は入力信号、yは出力信号、w1,w2は重みを表します. ○はノード、またはニューロンと呼ばれます.  
入力信号はそれぞれに固有の重みが乗算され、ニューロンに送られます.  ニューロンでは、送られてきた信号の総和(x1w1 + x2w2)に対して出力を行います.  その際、ある閾値(限界値)を超えると1を出力、閾値に満たない場合は0を出力します. 

入力と出力が直結し、単純化されたモデルを単純パーセプトロンといいます. 対して、入力と出力の間に層(中間層、隠れ層)があるモデルを多層パーセプトロンといいます.

パーセプトロンの動作原理を表す式

y = \left\{
\begin{array}{ll}
0 & (x_1 w_1 + x_2 w_2 \leq \phi) \\
1 & (x_1 w_1 + x_2 w_2 \gt \phi)
\end{array}
\right.

x : 入力信号, w : 重み, $ \phi $ : 閾値

閾値が扱いづらいのでマイナス値をつけて左辺に移項します. 移行したものを$b$ (バイアス)とします. バイアスは発火のしやすさ、しにくさを決めます. バイアスが大きい→発火しやすい(入力信号の総和が0を超えやすい).

y = \left\{
\begin{array}{ll}
0 & (b + x_1 w_1 + x_2 w_2 \leq 0) \\
1 & (b + x_1 w_1 + x_2 w_2 \gt 0)
\end{array}
\right.

2020-01-24 (4).png

パラメータ(バイアスと重み)を発火条件に沿うように調節します.

AND演算

import numpy as np

def AND(x1, x2):
    x1_x2 = np.array([x1, x2])
    b = -0.8
    w1_w2 = np.array([0.5, 0.5])
    tmp = b + np.sum(x1_x2 * w1_w2)
    if tmp <= 0:
        return 0
    elif tmp > 0:
        return 1
  • 入力xは0または1
  • ($x_1$, $x_2$)=(1, 1)のときのみ発火(計算結果が0を超える)

という条件に沿うようにパラメータを調節します.

($b$, $w_1$, $w_2$)に適当な値を代入します.
上のコードでは(-0.8, 0.5, 0.5)となっていますが、たとえば(-0.3, 0.2, 0.2)でも再現できます.

NAND演算はAND演算のバイアスと重みの符号を反転します.

OR演算

import numpy as np

def OR(x1, x2):
    x1_x2 = np.array([x1, x2])
    b = -0.3 #変更
    w1_w2 = np.array([0.5, 0.5])
    tmp = b + np.sum(x1_x2 * w1_w2)
    if tmp <= 0:
        return 0
    elif tmp > 0:
        return 1

バイアス$b$が変わりました.

XOR演算

import numpy as np

# NAND演算
def NAND(x1, x2):
    x1_x2 = np.array([x1, x2])
    b = 0.8
    w1_w2 = np.array([-0.5, -0.5])
    tmp = b + np.sum(x1_x2 * w1_w2)
    if tmp <= 0:
        return 0
    elif tmp > 0:
        return 1

# OR演算
def OR(x1, x2):
    x1_x2 = np.array([x1, x2])
    b = -0.3
    w1_w2 = np.array([0.5, 0.5])
    tmp = b + np.sum(x1_x2 * w1_w2)
    if tmp <= 0:
        return 0
    elif tmp > 0:
        return 1

# AND演算
def AND(x1, x2):
    x1_x2 = np.array([x1, x2])
    b = -0.8
    w1_w2 = np.array([0.5, 0.5])
    tmp = b + np.sum(x1_x2 * w1_w2)
    if tmp <= 0:
        return 0
    elif tmp > 0:
        return 1

# XOR演算
def XOR(x1, x2):
    nand_ = NAND(x1, x2)
    or_ = OR(x1, x2)
    xor_ = AND(nand_, or_)
    return xor_

XOR演算は入力と出力を直結したモデル(単純パーセプトロン)では表現できないので、中に層をかませます. 多層パーセプトロンです. 今回はNANDとORした結果をANDしました.
単純パーセプトロンで表現できないということは、線形分離不可能ということです. グラフを書いて確認してみてください.

さいごに

  • パーセプトロンはある入力を与えたとき、発火するか否かによって決まった値が出力される
  • パラメータとして重みとバイアスを持つ
  • 単純パーセプトロンは線形分離可能なモデルに使用する
  • 線形分離不可能なモデル場合、中間層をもった多層パーセプトロンを使用する

こんな感じでしょうか...

Why not register and get more from Qiita?
  1. We will deliver articles that match you
    By following users and tags, you can catch up information on technical fields that you are interested in as a whole
  2. you can read useful information later efficiently
    By "stocking" the articles you like, you can search right away
Comments
No comments
Sign up for free and join this conversation.
If you already have a Qiita account
Why do not you register as a user and use Qiita more conveniently?
You need to log in to use this function. Qiita can be used more conveniently after logging in.
You seem to be reading articles frequently this month. Qiita can be used more conveniently after logging in.
  1. We will deliver articles that match you
    By following users and tags, you can catch up information on technical fields that you are interested in as a whole
  2. you can read useful information later efficiently
    By "stocking" the articles you like, you can search right away
ユーザーは見つかりませんでした