Python
Inicializar detector y modelo
Vista de consulta del código. Los datos sensibles en URLs se ocultan en esta vista.
import os
import cv2
import numpy as np
from mtcnn import MTCNN
from keras_facenet import FaceNet
# Inicializar detector y modelo
detector = MTCNN()
embedder = FaceNet()
# Diccionario para almacenar embeddings
base_datos = {}
# -----------------------------------------
# FUNCIÓN PARA EXTRAER ROSTRO
# -----------------------------------------
def extraer_rostro(ruta_imagen):
imagen = cv2.imread(ruta_imagen)
if imagen is None:
return None
imagen_rgb = cv2.cvtColor(imagen, cv2.COLOR_BGR2RGB)
resultados = detector.detect_faces(imagen_rgb)
if len(resultados) == 0:
return None
x, y, ancho, alto = resultados[0]['box']
x, y = abs(x), abs(y)
rostro = imagen_rgb[y:y+alto, x:x+ancho]
rostro = cv2.resize(rostro, (160, 160))
return rostro
# -----------------------------------------
# GENERAR EMBEDDING
# -----------------------------------------
def generar_embedding(rostro):
rostro = rostro.astype('float32')
rostro = np.expand_dims(rostro, axis=0)
embedding = embedder.embeddings(rostro)
return embedding[0]
# -----------------------------------------
# CARGAR BASE DE DATOS
# -----------------------------------------
ruta_personas = "pruebacaras"
for persona in os.listdir(ruta_personas):
carpeta_persona = os.path.join(ruta_personas, persona)
embeddings_persona = []
for archivo in os.listdir(carpeta_persona):
ruta = os.path.join(carpeta_persona, archivo)
rostro = extraer_rostro(ruta)
if rostro is not None:
embedding = generar_embedding(rostro)
embeddings_persona.append(embedding)
if len(embeddings_persona) > 0:
promedio = np.mean(embeddings_persona, axis=0)
base_datos[persona] = promedio
print("Base de datos cargada correctamente")
# -----------------------------------------
# RECONOCIMIENTO
# -----------------------------------------
imagen_prueba = "prueba.jpg"
imagen = cv2.imread(imagen_prueba)
imagen_rgb = cv2.cvtColor(imagen, cv2.COLOR_BGR2RGB)
resultados = detector.detect_faces(imagen_rgb)
for resultado in resultados:
x, y, ancho, alto = resultado['box']
x, y = abs(x), abs(y)
rostro = imagen_rgb[y:y+alto, x:x+ancho]
rostro_red = cv2.resize(rostro, (160, 160))
embedding_prueba = generar_embedding(rostro_red)
nombre_detectado = "Desconocido"
distancia_minima = 999
for nombre, embedding_bd in base_datos.items():
distancia = np.linalg.norm(embedding_prueba - embedding_bd)
if distancia < distancia_minima:
distancia_minima = distancia
nombre_detectado = nombre
# Umbral de reconocimiento
if distancia_minima > 1.0:
nombre_detectado = "Desconocido"
# Dibujar rectángulo
cv2.rectangle(imagen, (x, y), (x+ancho, y+alto), (0,255,0), 2)
texto = f"{nombre_detectado} ({distancia_minima:.2f})"
cv2.putText(
imagen,
texto,
(x, y-10),
cv2.FONT_HERSHEY_SIMPLEX,
0.8,
(0,255,0),
2
)
# Mostrar imagen
cv2.imshow("Reconocimiento Facial", imagen)
cv2.waitKey(0)
cv2.destroyAllWindows()