TinyML. Comprimindo a rede neural

Agora os programadores se deparam com uma tarefa difícil - como implementar uma estrutura complicada como uma rede neural - em, digamos, uma pulseira? Como otimizar o consumo de energia do modelo? Qual é o preço dessa otimização, e quão justificada é a introdução de modelos em dispositivos pequenos e porque é impossível prescindir dela.





E qual é a utilidade?

Vamos imaginar um sensor industrial caro - 1000 medições por segundo, um sensor de temperatura, medição de vibração, transmissão de dados ao longo de 10 km, um processador poderoso - 20 milhões de operações por segundo! Sua função é enviar dados de temperatura, vibração, bem como os valores de outros parâmetros ao servidor para evitar quebras de equipamentos. Mas aí está o azar - 99% dos dados enviados por ele são inúteis, daí - uma perda líquida de eletricidade. E pode haver dezenas e centenas desses sensores em produção. 





, -   ? ? , ?     , " " " !"  TinyML.





Você vê um pico muito estranho no meio?  Mesmo uma pessoa que está assistindo as leituras dos instrumentos tem dificuldade em perceber, mas o modelo ML vai lidar com isso facilmente e "não perde" o momento
? , , " "

, , . "" : , , , , ..





Em contraste com a nuvem, a IA incorporada é executada no próprio dispositivo
, embedded ("") AI

- - . , , WiFi, Bluetooth .





- - . - , " ".





- - . , . , , ... . , ( - TinyML).





- - . - , , .





- - , int , float - .





Quantization

, . - , . , 32 . , 8 ? , .





- 1 . . , .





? . .





A multiplicação da matriz, neste caso, parece "um pouco" diferente
""

, , . , .





#     
x_values = np.random.uniform(
    low=0, high=2*math.pi, size=1000).astype(np.float32)

# 
np.random.shuffle(x_values)

y_values = np.sin(x_values).astype(np.float32)

#  ,   "   "
y_values += 0.1 * np.random.randn(*y_values.shape)

plt.plot(x_values, y_values, 'b.')
plt.show()
      
      



. , ( , ).





!





#   
model = tf.keras.Sequential()

model.add(keras.layers.Dense(16, activation='relu', input_shape=(1,)))

model.add(keras.layers.Dense(16, activation='relu'))

model.add(keras.layers.Dense(1))

model.compile(optimizer='adam', loss="mse", metrics=["mae"])

#  
history = model.fit(x_train, y_train, epochs=500, batch_size=64,
                    validation_data=(x_validate, y_validate))

# 
model.save(MODEL_TF)
      
      



, :





A qualidade resultante é adequada para nossos experimentos.

, . "" . TFLiteConverter, .





#      TensorFlow Lite   
converter = tf.lite.TFLiteConverter.from_saved_model(MODEL_TF)
model_no_quant_tflite = converter.convert()

# 
open(MODEL_NO_QUANT_TFLITE, "wb").write(model_no_quant_tflite)

#      TensorFlow Lite  
def representative_dataset():
  for i in range(500):
    yield([x_train[i].reshape(1, 1)])

converter.optimizations = [tf.lite.Optimize.DEFAULT]

#  ,         int
converter.target_spec.supported_ops = [tf.lite.OpsSet.TFLITE_BUILTINS_INT8]
converter.inference_input_type = tf.int8
converter.inference_output_type = tf.int8

#    ,    
converter.representative_dataset = representative_dataset
model_tflite = converter.convert()

open(MODEL_TFLITE, "wb").write(model_tflite)
      
      



: , TensorFlow Lite , TensorFlow Lite . , .





pd.DataFrame.from_records(
    [["TensorFlow", f"{size_tf} bytes", ""],
     ["TensorFlow Lite", f"{size_no_quant_tflite} bytes ", f"(reduced by {size_tf - size_no_quant_tflite} bytes)"],
     ["TensorFlow Lite Quantized", f"{size_tflite} bytes", f"(reduced by {size_no_quant_tflite - size_tflite} bytes)"]],
     columns = ["Model", "Size", ""], index="Model")
      
      



, , TensorFlow Lite 32% , 40% ! , , ?





, . , , !





Python , , , ? , . ! Ubuntu, Windows - .





#  xxd
!apt-get update && apt-get -qq install xxd
#   
!xxd -i {MODEL_TFLITE} > {MODEL_TFLITE_MICRO}
#   
REPLACE_TEXT = MODEL_TFLITE.replace('/', '_').replace('.', '_')
!sed -i 's/'{REPLACE_TEXT}'/g_model/g' {MODEL_TFLITE_MICRO}
#  ,       C  
!cat {MODEL_TFLITE_MICRO}
      
      



, 400.





, , , , . ( ) . , , - .






//   ,     

  float x = 0.0f;
  float y_true = sin(x);

  // 
  tflite::MicroErrorReporter micro_error_reporter;

  //    
  const tflite::Model* model = ::tflite::GetModel(g_model);
      
      



. ? , : , . - , . , .





, :





  x = 5.f;
  y_true = sin(x);
  input->data.int8[0] = x / input_scale + input_zero_point;
  interpreter.Invoke();
  y_pred = (output->data.int8[0] - output_zero_point) * output_scale;
  TF_LITE_MICRO_EXPECT_NEAR(y_true, y_pred, epsilon);
      
      



Edge Impulse

Edge Impulse , TinyML.





, , . , , , - .





- TinyML . ( , ..) . 20% , , .





, NoML Community - https://t.me/noml_community.








All Articles