2010-01-27 20 views
35

Aquí hay algunos temas que son muy útiles sobre cómo encontrar imágenes similares.OpenCV/SURF ¿Cómo generar una imagen hash/huella digital/firma fuera de los descriptores?

Lo que quiero hacer es conseguir una huella digital de una imagen y encontrar la misma imagen en diferentes fotos tomadas por una cámara digital. El algoritmo de SURF parece ser la mejor manera de ser independiente en escala, ángulo y otras distorsiones.

estoy usando OpenCV con el algoritmo SURF para extraer características de la imagen de la muestra sucesivamente. Ahora me pregunto cómo convertir todos estos datos de funciones (posición, laplacian, tamaño, orientación, arpillera) en una huella digital o hash.

Esta huella digital se almacena en una base de datos y una consulta de búsqueda debe ser capaz de comparar esa huella digital con una huella digital de una foto con casi las mismas características.

Actualización:

Parece que no hay manera de convertir todos los vectores de descriptores en un simple hash. Entonces, ¿cuál sería la mejor manera de almacenar los descriptores de imagen en la base de datos para consultas rápidas?

Would Vocabulario Árboles ser una opción?

estaría muy agradecido por cualquier ayuda.

+0

El código realiza lo que se llama juego "vecino más cercano" - tomando el descriptor (un vector de tamaño N) y comparándolo con un conjunto de otros vectores de tamaño N (esto puede ser calculando la distancia euclidiana entre ellos o cualquier otra medida de distancia) y seleccionando el que está más cerca. El ingenuo en el nombre significa que el vector se compara con TODOS los demás vectores. Hay otros algoritmos que usan el vecino más aproximado aproximado que son menos precisos pero más eficientes. – elijah

+1

Para abreviar: no se puede hacer una función hash de las imágenes (lo cual es demasiado peligroso y presuntuoso). Puede consultar la literatura para la clasificación de vecino más cercano o las medidas de similitud de imagen. – elijah

+0

De acuerdo, ¿cuál sería la mejor forma de almacenar cualquier consulta que los descriptores de imágenes? – dan

Respuesta

9

Los datos de función que mencionas (posición, laplaciano, tamaño, orientación, arpillera) no es suficiente para su propósito (estos son en realidad las partes menos relevantes del descriptor si usted quiere hacer juego). Los datos que desea mirar son los "descriptores" (el cuarto argumento):

void cvExtractSURF(const CvArr* image, const CvArr* mask, CvSeq** keypoints, CvSeq** descriptors, CvMemStorage* storage, CvSURFParams params)

Estos son 128 o 64 (dependiendo de params) vectores que contienen las "huellas digitales" de la función específica (cada uno la imagen contendrá una cantidad variable de tales vectores). Si tienes la versión más reciente de OPENCV tienen un find_obj.cpp llamado muestra, que muestra cómo se utiliza para hacer coincidir

actualización:

es posible encontrar this discusión útil

+0

Hola Liza, gracias por tu respuesta. Miré el ejemplo pero no encontré ninguna forma de transformar los vectores de los descriptores almacenados en CvSeq en un valor hash que permite almacenarlos en una base de datos y compararlos con otros hash. ¿Tienes alguna pista sobre eso? – dan

+0

el CvSeq simplemente almacena arrays float (mira el código fuente de cvExtractSURF para ver cómo lo almacenan). esas matrices (128 o 64 de longitud) son lo que te interesa en – elijah

+0

por cierto, si lo que quieres es obtener un hash mágico que mapee todas las imágenes de perro, por ejemplo, con el mismo código hash, me temo que es más más complicado que simplemente extraer las características de SURF. Eche un vistazo al enlace que puse en la actualización – elijah

3

Un trivial forma de calcular un hash sería el siguiente. Obtenga todos los descriptores de la imagen (por ejemplo, N de ellos). Cada descriptor es un vector de 128 números (puede convertirlos en enteros entre 0 y 255). Entonces tienes un conjunto de enteros N * 128. Simplemente escríbalos uno tras otro en una cadena y utilízalo como un valor hash. Si desea que los valores hash sean pequeños, creo que hay formas de calcular las funciones hash de cadenas, así que convierta descriptores a cadena y luego use el valor hash de esa cadena.

que podría funcionar si se desea buscar duplicados exactos. Pero parece (ya que habla de escala, rotación, etc.) que desea simplemente encontrar imágenes "similares". En ese caso, usar un hash probablemente no sea una buena forma de hacerlo. Probablemente use algún detector de puntos de interés para encontrar puntos en los que calcular los descriptores de SURF. Imagine que devolverá el mismo conjunto de puntos, pero en diferente orden. De repente, su valor de hash será muy diferente, incluso si las imágenes y los descriptores son los mismos.

Entonces, si tuviera que encontrar imágenes similares de manera confiable, usaría un enfoque diferente.Por ejemplo, podría cuantificar vectores los descriptores de SURF, construir histogramas de valores cuantificados de vectores y usar la intersección de histogramas para hacer correspondencias. ¿De verdad tienes que usar funciones hash (tal vez por eficiencia), o solo quieres usar lo que sea para encontrar imágenes similares?

+0

Hola Sheldon, gracias por su respuesta. Antes de mirar en SURF, estaba trabajando con el pHash lib. Esa lib genera un valor hash para los datos multimedia (imágenes, video y audio). De lo que podría utilizar la distancia de Hamming para consultar su base de datos de hashes de imágenes similares con bastante facilidad. Pensé que debe haber una manera de hacer lo mismo con los descriptores de SURF de alguna manera. Ahora estoy pensando en almacenar todos los objetos de matriz de descriptores de imagen serializados en la base de datos. Cuando quiero encontrar una imagen similar en la base de datos, tengo que seleccionar fila por fila y encontrar descripciones similares a mano. (...) – dan

+2

(continuación) La gran desventaja sería un rendimiento muy malo para una gran base de datos de imágenes. Me pregunto cómo TinEye.com podría encontrar imágenes similares tan rápidamente. Debe haber algún truco para consultar su base de datos muy rápido. – dan

+1

Creo que lo que ayudaría si dijera qué es exactamente lo que está tratando de lograr. Dada una imagen, ¿qué estás tratando de encontrar? Imágenes idénticas, imágenes similares, imágenes similares hasta rotación/escala de traducción? Dada una imagen X, ¿desea encontrar solo imágenes que sean similares a X, o también desea imágenes que contengan X como una subparte? Por ejemplo, la consulta es una imagen de la cara. ¿Desea buscar otras imágenes faciales, o también fotografías de cuerpo entero que contengan la cara pero también muchas otras cosas? ¿Por qué dejó de usar pHash y decidió trabajar con descriptores de SURF en su lugar? – user245973

2

Min-Hash o min-Hashing es una técnica que podría ayudarle. Codifica la imagen completa en una representación con tamaño ajustable que luego se almacena en tablas hash. Varias variantes como Geométrico min-Hashing, Partición min-Hash y Bundle min-Hashing existen. La huella de memoria resultante no es una de las más pequeñas, pero estas técnicas funcionan para una variedad de escenarios, como la recuperación casi duplicada e incluso la recuperación de objetos pequeños, un escenario donde otras firmas cortas a menudo no funcionan muy bien.

Hay varios artículos sobre este tema. literatura entrada sería: Cerca de detección de duplicados Image: min-hash y Ponderación TF-IDF Ondrej Chum, James Philbin, Andrew Zisserman, BMVC 2008PDF

Cuestiones relacionadas