Advertisement
Guest User

Untitled

a guest
May 27th, 2015
250
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
text 4.34 KB | None | 0 0
  1. # encoding: utf-8
  2.  
  3. '''
  4. Implementação da rede Perceptron
  5. Autor: Marcos Castro
  6. '''
  7.  
  8. import random, copy
  9.  
  10. class Perceptron:
  11.  
  12. def __init__(self, amostras, saidas, taxa_aprendizado=0.1, epocas=1000, limiar=-1):
  13.  
  14. self.amostras = amostras # todas as amostras
  15. self.saidas = saidas # saídas respectivas de cada amostra
  16. self.taxa_aprendizado = taxa_aprendizado # taxa de aprendizado (entre 0 e 1)
  17. self.epocas = epocas # número de épocas
  18. self.limiar = limiar # limiar
  19. self.num_amostras = len(amostras) # quantidade de amostras
  20. self.num_amostra = len(amostras[0]) # quantidade de elementos por cada amostra
  21. self.pesos = [] # vetor dos pesos
  22.  
  23.  
  24. # função utilizada para treinar a rede
  25. def treinar(self):
  26.  
  27. # adiciona -1 para cada amostra
  28. for amostra in self.amostras:
  29. amostra.insert(0, -1)
  30.  
  31. # inicia o vetor de pesos com valores aleatórios pequenos
  32. for i in range(self.num_amostra):
  33. self.pesos.append(random.random())
  34.  
  35. # insere o limiar no vetor de pesos
  36. self.pesos.insert(0, self.limiar)
  37.  
  38. num_epocas = 0 # inicia o contador de épocas
  39.  
  40. while True:
  41.  
  42. erro = False # erro inicialmente inexiste
  43.  
  44. # para todas as amostras de treinamento
  45. for i in range(self.num_amostras):
  46.  
  47. u = 0
  48. '''
  49. realiza o somatório, o limite (self.num_amostra + 1)
  50. é porque foi inserido o -1 em cada amostra
  51. '''
  52. for j in range(self.num_amostra + 1):
  53. u += self.pesos[j] * self.amostras[i][j]
  54.  
  55. # obtém a saída da rede utilizando a função de ativação
  56. y = self.sinal(u)
  57.  
  58. # verifica se a saída da rede é diferente da saída desejada
  59. if y != self.saidas[i]:
  60.  
  61. # calcula o erro: subtração entre a saída desejada e a saída da rede
  62. erro_aux = self.saidas[i] - y
  63.  
  64. # faz o ajuste dos pesos para cada elemento da amostra
  65. for j in range (self.num_amostra + 1):
  66. self.pesos[j] = self.pesos[j] + self.taxa_aprendizado * erro_aux * self.amostras[i][j]
  67.  
  68. erro = True # se entrou, é porque o erro ainda existe
  69.  
  70. num_epocas += 1 # incrementa o número de épocas
  71.  
  72. # critério de parada é pelo número de épocas ou se não existir erro
  73. if num_epocas > self.epocas or not erro:
  74. break
  75.  
  76.  
  77. # função utilizada para testar a rede
  78. # recebe uma amostra a ser classificada e os nomes das classes
  79. # utiliza função sinal, se é -1 então é classe1, senão é classe2
  80. def testar(self, amostra, classe1, classe2):
  81.  
  82. # insere o -1
  83. amostra.insert(0, -1)
  84.  
  85. '''
  86. utiliza-se o vetor de pesos ajustado
  87. durante o treinamento da rede
  88. '''
  89. u = 0
  90. for i in range(self.num_amostra + 1):
  91. u += self.pesos[i] * amostra[i]
  92.  
  93. # calcula a saída da rede
  94. y = self.sinal(u)
  95.  
  96. # verifica a qual classe pertence
  97. if y == -1:
  98. print('A amostra pertence a classe %s' % classe1)
  99. else:
  100. print('A amostra pertence a classe %s' % classe2)
  101.  
  102.  
  103. def degrau(self, u):
  104. return 1 if u >= 0 else 0
  105.  
  106.  
  107. def sinal(self, u): # é a mesma função degrau bipolar
  108. return 1 if u >= 0 else -1
  109.  
  110.  
  111. if __name__ == "__main__":
  112.  
  113.  
  114. print('\nA ou B?\n')
  115.  
  116. # todas as amostras (total de 4 amostras)
  117. amostras = [[0.1, 0.4, 0.7], [0.3, 0.7, 0.2],
  118. [0.6, 0.9, 0.8], [0.5, 0.7, 0.1]]
  119.  
  120. # saídas desejadas de cada amostra
  121. saidas = [1, -1, -1, 1]
  122.  
  123. # conjunto de amostras de testes
  124. testes = copy.deepcopy(amostras)
  125.  
  126. # cria uma rede Perceptron
  127. rede = Perceptron(amostras=amostras, saidas=saidas,
  128. taxa_aprendizado=0.1, epocas=1000)
  129.  
  130. # treina a rede
  131. rede.treinar()
  132.  
  133. for teste in testes:
  134. rede.testar(teste, 'A', 'B')
  135.  
  136.  
  137. '''
  138. Outro caso de teste: classificando cores
  139. '''
  140.  
  141. print('\nBlue ou Red?\n')
  142.  
  143. amostras2 = [ [0.72, 0.82], [0.91, -0.69],
  144. [0.46, 0.80], [0.03, 0.93],
  145. [0.12, 0.25], [0.96, 0.47],
  146. [0.8, -0.75], [0.46, 0.98],
  147. [0.66, 0.24], [0.72, -0.15],
  148. [0.35, 0.01], [-0.16, 0.84],
  149. [-0.04, 0.68], [-0.11, 0.1],
  150. [0.31, -0.96], [0.0, -0.26],
  151. [-0.43, -0.65], [0.57, -0.97],
  152. [-0.47, -0.03], [-0.72, -0.64],
  153. [-0.57, 0.15], [-0.25, -0.43],
  154. [0.47, -0.88], [-0.12, -0.9],
  155. [-0.58, 0.62], [-0.48, 0.05],
  156. [-0.79, -0.92], [-0.42, -0.09],
  157. [-0.76, 0.65], [-0.77, -0.76]]
  158.  
  159. saidas2 = [-1,-1,-1,-1,-1,-1, -1,-1,
  160. -1,-1,-1,-1,-1,1,1,1,1,
  161. 1,1,1,1,1,1,1,1,1,1,1,1,1]
  162.  
  163. testes2 = copy.deepcopy(amostras2)
  164.  
  165. rede2 = Perceptron(amostras=amostras2, saidas=saidas2,
  166. taxa_aprendizado=0.1, epocas=1000)
  167.  
  168. rede2.treinar()
  169.  
  170. for teste in testes2:
  171. rede2.testar(teste, 'Red', 'Blue')
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement