algorithm - tag - ¿Cómo puedo detectar estas anomalías de audio?
tag id3 (5)
Creo que el siguiente algoritmo se puede aplicar a las muestras para determinar un posible falso positivo:
Primero, busque una alta cantidad de alta frecuencia, ya sea mediante FFT haciendo el bloque de sonido por bloque (tal vez 256 valores), o contando las muestras consecutivas por encima y por debajo de cero. Este último debe realizar un seguimiento del máximo consecutivo por encima de cero, máximo consecutivo por debajo de cero, la cantidad de pequeñas transiciones alrededor de cero y el volumen actual del bloque (0..1 como lo muestra Audacity). Luego, si el máximo consecutivo es inferior a 5 (el muestreo en 44100 y los ceros son consecutivos, mientras que las muestras destacadas son únicas, 5 responde a una frecuencia de 4410Hz, que es bastante alta), o la suma de las longitudes de las pequeñas transiciones es superior a un cierto valor dependiendo del máximo consecutivo (creo que la primera aproximación sería 3 * 5 * tamaño de bloque / distancia entre dos máximos, lo que equivale aproximadamente al período de la frecuencia FFT más alta. También debe medirse tanto por encima como por debajo del umbral, ya que podemos finalizar con un pico erróneo, que probablemente se detectará por la diferencia entre el tempo principal medido en los máximos por debajo de cero o por encima de cero, también por la desviación estándar de los picos. Si la frecuencia alta es dominante, este bloque solo es elegible para el valor cero Se necesitarán pruebas y un medio especial para reparar los datos. Si la alta frecuencia es significativa, es decir, si se detecta una baja frecuencia dominante, podemos buscar picos más grandes que el volumen de alta frecuencia de 3.0 *, así como ceros anormales en este bloque .
Además, sus brechas parecen ser altamente extendidas o cero, con altas extensiones para ser errores simples y cero errores desde 1-20. Entonces, si hay un rango de cero con valores por debajo del valor absoluto de 0.02, que está directamente rodeado por valores de 0.15 (una variable a ser definida) o un valor absoluto más alto Y del mismo signo, cuente este punto como un error. Los valores únicos que se destacan se pueden detectar si calcula 2.0*(current sample)-(previous sample)-(next sample)
y si está por encima de un cierto umbral (0.1 + volumen de alta frecuencia o 3.0 * volumen de alta frecuencia, lo que sea más grande), cuenta esto como un error y media.
Qué hacer con cero huecos encontrados: podemos copiar valores de 1 período hacia atrás y 1 período hacia adelante (promediado), donde "período" es de la frecuencia más significativa de la FFT del bloque. Si el "período" es más pequeño que el espacio (digamos que hemos detectado un espacio de ceros en una parte aguda del sonido), use dos o más períodos, por lo que todos los datos de origen serán válidos (en este caso, no se puede hacer un promedio, ya que es posible que la señal 2 periodos adelante de la brecha y 2 periodos atrás esté en contrafase). Si hay más de una frecuencia de aproximadamente la misma amplitud, podemos muestrearlas con las fases correctas, cortando el resto de las frecuencias menos significativas por completo.
La muestra sobresaliente debe IMO solo promediarse entre 2 y 4 muestras circundantes, ya que parece que solo se ha encontrado una muestra en sus archivos de sonido.
iOS tiene un problema de grabación a través de algunos dispositivos de audio USB. No se puede reproducir de manera confiable (ocurre cada 1 en ~ 2000-3000 registros en lotes y desaparece silenciosamente), y actualmente revisamos manualmente nuestro audio para detectar cualquier problema de grabación. Da como resultado que un pequeño número de muestras (1-20) se desplace por un número pequeño que suena como una especie de "crujido".
Se ven así:
más cerca:
más cerca:
otro error de muestra única en otro lugar en el mismo archivo de audio:
La pregunta es, ¿cómo se pueden detectar algorítmicamente (asumiendo un acceso directo a las muestras) mientras no se activan falsos positivos en el audio de alta frecuencia con formas de onda como esta?
Puntos extra: después de determinar tantos errores como sea posible, ¿cómo se puede "arreglar" el audio?
- Archivo de audio sucio - en la foto
- Otro archivo de audio sucio
- Audio limpio con alta frecuencia válida - en la foto
Más puntos de bonificación: lo que podría estar causando este problema en los controladores / hardware de audio USB de iOS (suponiendo que estén ahí).
La transformada de wavelet discreta (DWT) puede ser la solución a su problema.
Un cálculo de FFT no es muy útil en su caso, ya que es una representación promedio del contenido de frecuencia relativa durante toda la duración de la señal y, por lo tanto, es imposible detectar cambios momentáneos. La transformada de frecuencia de tiempo corto (STFT) se trata de solucionar esto calculando la DFT para bloques de tiempo consecutivos cortos de la señal, cuya longitud se determina por la longitud (y la forma) de una ventana, pero desde la resolución de la ventana. DFT depende de los datos / longitud de bloque, hay una compensación entre la resolución en frecuencia O en el tiempo, ¡y encontrar este tamaño de ventana fijo mágico puede ser complicado!
Lo que desea es un método de análisis de frecuencia de tiempo con una buena resolución de tiempo para eventos de alta frecuencia y una buena resolución de frecuencia para eventos de baja frecuencia ... ¡Ingrese la transformada discreta de wavelet!
Existen numerosas transformaciones wavelet para diferentes aplicaciones y, como es de esperar, es computacionalmente pesada. El DWT puede no ser una solución práctica para su problema, pero vale la pena considerarlo. Buena suerte con tu problema. Algunos viernes por la noche leyendo:
http://etd.lib.fsu.edu/theses/available/etd-11242003-185039/unrestricted/09_ds_chapter2.pdf
No creo que haya una solución inmediata para encontrar las perturbaciones, pero aquí hay una manera (no estándar) de abordar el problema. Usando esto, pude encontrar la mayoría de los intervalos y solo obtuve un pequeño número de falsos positivos, pero el algoritmo ciertamente podría usar algunos ajustes finos.
Mi idea es encontrar el punto de inicio y final de las muestras que se desvían. El primer paso debe ser hacer que estos puntos se destaquen más claramente. Esto se puede hacer tomando el logaritmo de los datos y tomando las diferencias entre valores consecutivos.
En MATLAB cargo los datos (en este ejemplo uso dirty-sample-other.wav)
y1 = wavread(''dirty-sample-pictured.wav'');
y2 = wavread(''dirty-sample-other.wav'');
y3 = wavread(''clean-highfreq.wav'');
data = y2;
y usa el siguiente código:
logdata = log(1+data);
difflogdata = diff(logdata);
Así que en lugar de esta trama de los datos originales:
obtenemos:
Donde los intervalos que buscamos se destacan como un pico positivo y negativo. Por ejemplo, al ampliar el valor positivo más grande en la gráfica de las diferencias logarítmicas, obtenemos las siguientes dos cifras. Uno para los datos originales:
y uno para la diferencia de logaritmos:
Esta gráfica podría ayudar a encontrar las áreas manualmente, pero lo ideal es que las encontremos usando un algoritmo. La forma en que lo hice fue tomar una ventana móvil de tamaño 6, calculando el valor medio de la ventana (de todos los puntos excepto el valor mínimo) y compararlo con el valor máximo. Si el punto máximo es el único punto que está por encima del valor medio y al menos el doble que el promedio, se cuenta como un valor extremo positivo.
Luego utilicé un umbral de conteos, al menos la mitad de las ventanas que se mueven sobre el valor deberían detectarlo como un valor extremo para que sea aceptado.
Al multiplicar todos los puntos con (-1), este algoritmo se ejecuta nuevamente para detectar los valores mínimos.
Marcando los extremos positivos con "o" y los extremos negativos con "*" obtenemos las siguientes dos parcelas. Una para las diferencias de logaritmos:
y uno para los datos originales:
Haciendo zoom en la parte izquierda de la figura que muestra las diferencias logarítmicas, podemos ver que se encuentran los valores más extremos:
Parece que la mayoría de los intervalos se encuentran y hay solo un pequeño número de falsos positivos. Por ejemplo, al ejecutar el algoritmo en ''clean-highfreq.wav''
solo encuentro un valor extremo positivo y otro negativo.
Los valores individuales que se clasifican falsamente como valores extremos podrían tal vez eliminarse al hacer coincidir los puntos de inicio y final. Y si desea reemplazar los datos perdidos, podría utilizar algún tipo de interpolación utilizando los puntos de datos circundantes, tal vez incluso una interpolación lineal sea lo suficientemente buena.
Aquí está el código MATLAB que utilicé:
function test20()
clc
clear all
y1 = wavread(''dirty-sample-pictured.wav'');
y2 = wavread(''dirty-sample-other.wav'');
y3 = wavread(''clean-highfreq.wav'');
data = y2;
logdata = log(1+data);
difflogdata = diff(logdata);
figure,plot(data),hold on,plot(data,''.'')
figure,plot(difflogdata),hold on,plot(difflogdata,''.'')
figure,plot(data),hold on,plot(data,''.''),xlim([68000,68200])
figure,plot(difflogdata),hold on,plot(difflogdata,''.''),xlim([68000,68200])
k = 6;
myData = difflogdata;
myPoints = findPoints(myData,k);
myData2 = -difflogdata;
myPoints2 = findPoints(myData2,k);
figure
plotterFunction(difflogdata,myPoints>=k,''or'')
hold on
plotterFunction(difflogdata,myPoints2>=k,''*r'')
figure
plotterFunction(data,myPoints>=k,''or'')
hold on
plotterFunction(data,myPoints2>=k,''*r'')
end
function myPoints = findPoints(myData,k)
iterationVector = k+1:length(myData);
myPoints = zeros(size(myData));
for i = iterationVector
subVector = myData(i-k:i);
meanSubVector = mean(subVector(subVector>min(subVector)));
[maxSubVector, maxIndex] = max(subVector);
if (sum(subVector>meanSubVector) == 1 && maxSubVector>2*meanSubVector)
myPoints(i-k-1+maxIndex) = myPoints(i-k-1+maxIndex) +1;
end
end
end
function plotterFunction(allPoints,extremeIndices,markerType)
extremePoints = NaN(size(allPoints));
extremePoints(extremeIndices) = allPoints(extremeIndices);
plot(extremePoints,markerType,''MarkerSize'',15),
hold on
plot(allPoints,''.'')
plot(allPoints)
end
Editar - comentarios sobre la recuperación de los datos originales
Aquí hay una vista ligeramente alejada de la figura tres arriba: (la perturbación está entre 6.8 y 6.82)
Cuando examino los valores, su teoría sobre los datos que se reflejan en valores negativos no parece ajustarse exactamente al patrón. Pero en cualquier caso, mi idea de simplemente eliminar las diferencias ciertamente no es correcta. Dado que los puntos circundantes no parecen estar alterados por la perturbación, probablemente volvería a la idea original de no confiar en los puntos dentro de la región afectada y, en cambio, utilizar algún tipo de interpolación utilizando los datos circundantes. Parece que una simple interpolación lineal sería una buena aproximación en la mayoría de los casos.
Para responder a la pregunta de por qué sucede:
Un dispositivo de audio USB y el host no son sincronizados con el reloj, es decir, el host no puede recuperar con precisión la relación entre el reloj local del host y el reloj de palabras del ADC / DAC en la interfaz de audio. Existen varias técnicas para la recuperación del reloj con diversos grados de efectividad. Para aumentar el problema, es probable que el reloj del bus no esté relacionado con ninguno de los dos relojes de audio.
Si bien puede imaginar que esto no es demasiado preocupante para la recepción de audio, las devoluciones de llamadas de captura de audio pueden ocurrir cuando hay datos; las interfaces de audio suelen ser bidireccionales y el host procesará el audio a intervalos regulares, que es el otro extremo. potencialmente consumiendo a una tasa ligeramente diferente.
En el medio hay varios conjuntos de búferes, que pueden sobrepasarse o no ejecutarse, que es lo que parece estar sucediendo aquí; El intervalo entre lo que está sucediendo ciertamente parece correcto.
Es posible que ayude a cambiar el dispositivo de audio USB a uno construido alrededor de un conjunto de chips diferente (o, simplemente, un oscilador local diferente).
Además, tanto el audio IEEE1394 como el flujo de transporte MPEG tienen el mismo requisito de recuperación de reloj. Ambos resuelven el problema incorporando un paquete de referencia de reloj local en el flujo de bits en serie de una manera muy predecible que permite una recuperación precisa del reloj en el otro extremo.
Puedes probar el siguiente enfoque súper simple (quizás sea suficiente):
- Toma cada punto de tu forma de onda y resta su predecesor (mira los cambios de un punto a otro).
- Mira la distribución de estos cambios y encuentra su desviación estándar.
- Si alguna diferencia dada supera X veces esta desviación estándar (ya sea arriba o abajo), márquela como un problema.
- Determine el mejor valor para X jugando con él y viendo qué tan bien se desempeña.
- La mayoría de los "problemas" deberían venir como un par de dos diferencias más allá de su límite, una subiendo y otra bajando.
Para seguir con el enfoque súper simple, puede corregir los datos simplemente interpolando linealmente entre el último punto bueno antes de la sección de problemas y el primer punto bueno después. (Asegúrese de no eliminar los puntos, ya que esto influirá (aumentará) el tono de su audio).