MapReduce es un modelo de programación y una implementación asociada para procesar y generar grandes conjuntos de datos con un algoritmo distribuido paralelo en un clúster . [1] [2] [3]
Un programa MapReduce se compone de un procedimiento de mapa , que realiza filtrado y clasificación (como ordenar a los estudiantes por nombre en colas, una cola para cada nombre), y un método de reducción , que realiza una operación de resumen (como contar el número de estudiantes en cada cola, lo que arroja frecuencias de nombres). El "Sistema MapReduce" (también llamado "infraestructura" o "marco") organiza el procesamiento reuniendo los servidores distribuidos, ejecutando las diversas tareas en paralelo, gestionando todas las comunicaciones y transferencias de datos entre las distintas partes del sistema y proporcionando redundancia . y tolerancia a fallos .
El modelo es una especialización de la estrategia dividir, aplicar y combinar para el análisis de datos. [4] Está inspirado en las funciones map y reduce comúnmente utilizadas en programación funcional , [5] aunque su propósito en el framework MapReduce no es el mismo que en sus formas originales. [6] Las contribuciones clave del marco MapReduce no son las funciones de mapa y reducción reales (que, por ejemplo, se parecen a las operaciones de reducción [ 8 ] y dispersión [9] del estándar Message Passing Interface de 1995 ), sino la escalabilidad y Tolerancia a fallas lograda para una variedad de aplicaciones debido a la paralelización. Como tal, una implementación de MapReduce de un solo subproceso generalmente no es más rápida que una implementación tradicional (que no sea MapReduce); Por lo general, cualquier ganancia solo se observa con implementaciones de subprocesos múltiples en hardware multiprocesador. [10] El uso de este modelo es beneficioso solo cuando entran en juego la operación aleatoria distribuida optimizada (que reduce el costo de comunicación de la red) y las características de tolerancia a fallas del marco MapReduce. Optimizar el costo de la comunicación es esencial para un buen algoritmo MapReduce. [11]
Las bibliotecas MapReduce se han escrito en muchos lenguajes de programación, con diferentes niveles de optimización. Una implementación popular de código abierto que admite reproducción aleatoria distribuida es parte de Apache Hadoop . El nombre MapReduce originalmente se refería a la tecnología patentada de Google , pero desde entonces se ha generalizado . En 2014, Google ya no usaba MapReduce como su principal modelo de procesamiento de big data , [12] y el desarrollo en Apache Mahout había pasado a mecanismos más capaces y menos orientados al disco que incorporaban mapas completos y capacidades reducidas. [13]
MapReduce es un marco para procesar problemas paralelizables en grandes conjuntos de datos utilizando una gran cantidad de computadoras (nodos), denominados colectivamente un clúster (si todos los nodos están en la misma red local y usan hardware similar) o una cuadrícula (si los nodos están compartidos entre sistemas distribuidos geográfica y administrativamente y utilizan hardware más heterogéneo). El procesamiento puede ocurrir en datos almacenados en un sistema de archivos (no estructurado) o en una base de datos (estructurada). MapReduce puede aprovechar la localidad de los datos, procesándolos cerca del lugar donde están almacenados para minimizar la sobrecarga de comunicación.
Un marco (o sistema) MapReduce generalmente se compone de tres operaciones (o pasos):
map
función a los datos locales y escribe la salida en un almacenamiento temporal. Un nodo maestro garantiza que solo se procese una copia de los datos de entrada redundantes.map
función), de modo que todos los datos que pertenecen a una clave se encuentran en el mismo nodo trabajador.MapReduce permite el procesamiento distribuido del mapa y operaciones de reducción. Los mapas se pueden realizar en paralelo, siempre que cada operación de mapeo sea independiente de las demás; en la práctica, esto está limitado por la cantidad de fuentes de datos independientes y/o la cantidad de CPU cercanas a cada fuente. De manera similar, un conjunto de 'reductores' puede realizar la fase de reducción, siempre que todas las salidas de la operación del mapa que comparten la misma clave se presenten al mismo reductor al mismo tiempo, o que la función de reducción sea asociativa . Si bien este proceso a menudo parece ineficiente en comparación con algoritmos que son más secuenciales (porque se deben ejecutar múltiples instancias del proceso de reducción), MapReduce se puede aplicar a conjuntos de datos significativamente más grandes que los que un solo servidor "comercial" puede manejar; una gran granja de servidores puede usar MapReduce para ordenar un petabyte de datos en sólo unas pocas horas. [14] El paralelismo también ofrece alguna posibilidad de recuperación de fallas parciales de los servidores o del almacenamiento durante la operación: si un mapeador o reductor falla, el trabajo se puede reprogramar, suponiendo que los datos de entrada aún estén disponibles.
Otra forma de ver MapReduce es como un cálculo distribuido y paralelo de 5 pasos:
Lógicamente se puede considerar que estos cinco pasos se ejecutan en secuencia (cada paso comienza sólo después de que se completa el paso anterior), aunque en la práctica pueden intercalarse siempre que el resultado final no se vea afectado.
En muchas situaciones, es posible que los datos de entrada ya se hayan distribuido ( "fragmentados" ) entre muchos servidores diferentes, en cuyo caso el paso 1 a veces podría simplificarse enormemente asignando servidores de mapas que procesarían los datos de entrada presentes localmente. De manera similar, el paso 3 a veces podría acelerarse asignando procesadores Reducir que estén lo más cerca posible de los datos generados por el mapa que necesitan procesar.
Las funciones Map y Reduce de MapReduce están definidas con respecto a datos estructurados en pares (clave, valor). Map toma un par de datos con un tipo en un dominio de datos y devuelve una lista de pares en un dominio diferente:
Map(k1,v1)
→list(k2,v2)
La función Mapa se aplica en paralelo a cada par (codificado por k1
) en el conjunto de datos de entrada. Esto produce una lista de pares (tecleados por k2
) para cada llamada. Después de eso, el marco MapReduce recopila todos los pares con la misma clave ( k2
) de todas las listas y los agrupa, creando un grupo para cada clave.
Luego, la función Reducir se aplica en paralelo a cada grupo, lo que a su vez produce una colección de valores en el mismo dominio:
Reduce(k2, list (v2))
→ list((k3, v3))
[15]
Cada llamada de Reduce normalmente produce un par clave-valor o un retorno vacío, aunque se permite que una llamada devuelva más de un par clave-valor. Las devoluciones de todas las llamadas se recopilan como la lista de resultados deseados.
Por lo tanto, el marco MapReduce transforma una lista de pares (clave, valor) en otra lista de pares (clave, valor). [16] Este comportamiento es diferente de la típica combinación de mapa de programación funcional y reducción, que acepta una lista de valores arbitrarios y devuelve un valor único que combina todos los valores devueltos por el mapa.
Es necesario, pero no suficiente, tener implementaciones del mapa y reducir las abstracciones para poder implementar MapReduce. Las implementaciones distribuidas de MapReduce requieren un medio para conectar los procesos que realizan las fases de Mapa y Reducción. Este puede ser un sistema de archivos distribuido . Son posibles otras opciones, como la transmisión directa desde los mapeadores a los reductores, o que los procesadores de mapeo entreguen sus resultados a los reductores que los consultan.
El ejemplo canónico de MapReduce cuenta la aparición de cada palabra en un conjunto de documentos: [17]
mapa de funciones (nombre de cadena, documento de cadena): // nombre: nombre del documento // documento: contenido del documento para cada palabra w en el documento: emitir (w, 1)función reducir (palabra de cadena, iterador recuentos parciales): // palabra: una palabra // recuentos parciales: una lista de recuentos parciales agregados suma = 0 para cada pc en recuentos parciales: suma += pc emitir (palabra, suma)
Aquí, cada documento se divide en palabras y cada palabra se cuenta mediante la función de mapa , utilizando la palabra como clave de resultado. El marco reúne todos los pares con la misma clave y los envía a la misma llamada para reducir . Por lo tanto, esta función sólo necesita sumar todos sus valores de entrada para encontrar el total de apariciones de esa palabra.
Como otro ejemplo, imaginemos que para una base de datos de 1.100 millones de personas, uno quisiera calcular el número promedio de contactos sociales que tiene una persona según su edad. En SQL , dicha consulta podría expresarse como:
SELECCIONE edad , AVG ( contactos ) DE las redes sociales . persona GRUPAR POR edad ORDENAR POR edad
Con MapReduce, los valores de la clave K1 podrían ser los números enteros del 1 al 1100, cada uno de los cuales representa un lote de 1 millón de registros, el valor de la clave K2 podría ser la edad de una persona en años y este cálculo se podría lograr usando las siguientes funciones:
Se ingresa la función Map : entero K1 entre 1 y 1100, que representa un lote de 1 millón de registros social.person para cada registro social.person en el lote K1, sea Y la edad de la persona , sea N el número de contactos que la persona ha producido . un registro de salida (Y,(N,1)) función de fin de repeticiónfunción Reducir es entrada: edad (en años) Y para cada registro de entrada (Y,(N,C)) hacer Acumular en S la suma de N*C Acumular en C nuevo la suma de C repetir sea A ser S/C nuevo producir un registro de salida (Y,(A,C nuevo )) función final
Tenga en cuenta que en la función Reducir , C es el recuento de personas que tienen en total N contactos, por lo que en la función Mapa es natural escribir C=1 , ya que cada par de salida se refiere a los contactos de una sola persona.
El sistema MapReduce alinearía los 1100 procesadores de mapas y proporcionaría a cada uno su correspondiente millón de registros de entrada. El paso Map produciría 1,1 mil millones (Y,(N,1)) registros, con valores Y que oscilan entre, digamos, 8 y 103. Luego, el sistema MapReduce alinearía los 96 procesadores Reduce realizando una operación de barajado de la clave/valor. pares debido al hecho de que necesitamos un promedio por edad y proporcionar a cada uno sus millones de registros de entrada correspondientes. El paso Reducir daría como resultado un conjunto muy reducido de solo 96 registros de salida (Y,A) , que se colocarían en el archivo de resultados final, ordenados por Y .
La información del recuento en el registro es importante si el procesamiento se reduce más de una vez. Si no sumamos el recuento de registros, el promedio calculado sería incorrecto, por ejemplo:
-- salida del mapa #1: edad, cantidad de contactos10, 910, 910, 9
-- salida del mapa #2: edad, cantidad de contactos10, 910, 9
-- salida del mapa #3: edad, cantidad de contactos10, 10
Si reducimos los archivos #1 y #2 , tendremos un nuevo archivo con una media de 9 contactos para una persona de 10 años ((9+9+9+9+9)/5):
-- reducir el paso #1: edad, promedio de contactos10, 9
Si lo reducimos con el archivo #3 , perdemos la cuenta de cuántos registros ya hemos visto, por lo que terminamos con una media de 9,5 contactos para una persona de 10 años ((9+10)/2) , Cuál está mal. La respuesta correcta es 9,1 66 = 55 / 6 = (9×3+9×2+10×1)/(3+2+1).
La arquitectura del marco de software se adhiere al principio abierto-cerrado donde el código se divide efectivamente en puntos congelados no modificables y puntos calientes extensibles . El punto congelado del marco MapReduce es un tipo distribuido grande. Los puntos calientes que define la aplicación son:
El lector de entrada divide la entrada en 'divisiones' de tamaño apropiado (en la práctica, normalmente, de 64 MB a 128 MB) y el marco asigna una división a cada función de Mapa . El lector de entrada lee datos del almacenamiento estable (normalmente, un sistema de archivos distribuido ) y genera pares clave/valor.
Un ejemplo común leerá un directorio lleno de archivos de texto y devolverá cada línea como un registro.
La función Mapa toma una serie de pares clave/valor, procesa cada uno y genera cero o más pares clave/valor de salida. Los tipos de entrada y salida del mapa pueden ser (y a menudo son) diferentes entre sí.
Si la aplicación está contando palabras, la función de mapa dividirá la línea en palabras y generará un par clave/valor para cada palabra. Cada par de salida contendría la palabra como clave y el número de instancias de esa palabra en la línea como valor.
La función de partición de la aplicación asigna cada salida de la función de mapa a un reductor particular para fines de fragmentación . La función de partición recibe la clave y el número de reductores y devuelve el índice del reductor deseado .
Un valor predeterminado típico es aplicar hash a la clave y utilizar el valor hash módulo del número de reductores . Es importante elegir una función de partición que proporcione una distribución aproximadamente uniforme de datos por fragmento para fines de equilibrio de carga ; de lo contrario, la operación MapReduce puede retrasarse esperando a que finalicen los reductores lentos (es decir, los reductores asignaron las partes más grandes de los no particiones). datos particionados uniformemente).
Entre las etapas de mapa y reducción, los datos se mezclan (se clasifican en paralelo/se intercambian entre nodos) para mover los datos desde el nodo del mapa que los produjo al fragmento en el que se reducirán. A veces, la reproducción aleatoria puede tardar más que el tiempo de cálculo, dependiendo del ancho de banda de la red, las velocidades de la CPU, los datos producidos y el tiempo que tarda el mapa y reduce los cálculos.
La entrada para cada Reducción se extrae de la máquina donde se ejecutó el Mapa y se clasifica utilizando la función de comparación de la aplicación .
El marco llama a la función Reducir de la aplicación una vez para cada clave única en el orden ordenado. Reducir puede iterar a través de los valores asociados con esa clave y producir cero o más resultados .
En el ejemplo del recuento de palabras, la función Reducir toma los valores de entrada, los suma y genera una salida única de la palabra y la suma final.
El Output Writer escribe la salida de Reduce en el almacenamiento estable.
Las propiedades de los monoides son la base para garantizar la validez de las operaciones de MapReduce. [18] [19]
En el paquete Algebird [20], una implementación Scala de Map/Reduce requiere explícitamente un tipo de clase monoide. [21]
Las operaciones de MapReduce tratan con dos tipos: el tipo A de datos de entrada que se asignan y el tipo B de datos de salida que se reducen.
La operación Map toma valores individuales de tipo A y produce, para cada a:A un valor b:B ; La operación Reducir requiere una operación binaria • definida sobre valores de tipo B ; Consiste en plegar todos los b:B disponibles a un solo valor.
Desde el punto de vista de los requisitos básicos, cualquier operación de MapReduce debe implicar la capacidad de reagrupar arbitrariamente los datos que se están reduciendo. Tal requisito equivale a dos propiedades de la operación •:
La segunda propiedad garantiza que, cuando se paraleliza sobre múltiples nodos, los nodos que no tienen datos para procesar no tendrán ningún impacto en el resultado.
Estas dos propiedades equivalen a tener un monoide ( B , • , e ) en valores de tipo B con operación • y con elemento neutro e .
No hay requisitos sobre los valores del tipo A ; Se puede utilizar una función arbitraria A → B para la operación de mapa . Esto significa que tenemos un catamorfismo A* → ( B , •, e ). Aquí A* denota una estrella Kleene , también conocida como el tipo de listas sobre A.
La operación Shuffle per se no está relacionada con la esencia de MapReduce; es necesario para distribuir los cálculos a través de la nube.
De lo anterior se deduce que no todas las operaciones binarias de Reducción funcionarán en MapReduce. Aquí están los contraejemplos:
No se garantiza que los programas MapReduce sean rápidos. El principal beneficio de este modelo de programación es explotar la operación aleatoria optimizada de la plataforma y solo tener que escribir las partes Mapa y Reducir del programa. Sin embargo, en la práctica, el autor de un programa MapReduce debe tener en cuenta el paso aleatorio; en particular, la función de partición y la cantidad de datos escritos por la función Mapa pueden tener un gran impacto en el rendimiento y la escalabilidad. Los módulos adicionales, como la función Combiner , pueden ayudar a reducir la cantidad de datos escritos en el disco y transmitidos a través de la red. Las aplicaciones MapReduce pueden lograr aceleraciones sublineales en circunstancias específicas. [22]
Al diseñar un algoritmo MapReduce, el autor debe elegir un buen equilibrio [11] entre los costos de cálculo y comunicación. El costo de comunicación a menudo domina el costo de cálculo, [11] [22] y muchas implementaciones de MapReduce están diseñadas para escribir todas las comunicaciones en el almacenamiento distribuido para la recuperación de fallos.
Al ajustar el rendimiento de MapReduce, se debe tener en cuenta la complejidad de mapear, mezclar, ordenar (agrupar por clave) y reducir. La cantidad de datos producidos por los mapeadores es un parámetro clave que desplaza la mayor parte del costo de cálculo entre mapeo y reducción. La reducción incluye la clasificación (agrupación de claves) que tiene una complejidad no lineal. Por lo tanto, los tamaños de partición pequeños reducen el tiempo de clasificación, pero existe una compensación porque tener una gran cantidad de reductores puede resultar poco práctico. La influencia del tamaño de la unidad dividida es marginal (a menos que se elija particularmente mal, digamos <1 MB). Las ganancias de algunos mapeadores que leen la carga de los discos locales, en promedio, son menores. [23]
Para procesos que se completan rápidamente y donde los datos caben en la memoria principal de una sola máquina o de un pequeño clúster, el uso de un marco MapReduce generalmente no es efectivo. Dado que estos marcos están diseñados para recuperarse de la pérdida de nodos completos durante el cálculo, escriben resultados provisionales en el almacenamiento distribuido. Esta recuperación de fallas es costosa y solo vale la pena cuando el cálculo involucra muchas computadoras y un tiempo de ejecución prolongado. Una tarea que se completa en segundos puede simplemente reiniciarse en caso de error, y la probabilidad de que al menos una máquina falle aumenta rápidamente con el tamaño del clúster. En tales problemas, las implementaciones que mantienen todos los datos en la memoria y simplemente reinician un cálculo en caso de fallas de nodos o, cuando los datos son lo suficientemente pequeños, soluciones no distribuidas, a menudo serán más rápidas que un sistema MapReduce.
MapReduce logra confiabilidad al dividir una cantidad de operaciones en el conjunto de datos en cada nodo de la red. Se espera que cada nodo informe periódicamente sobre el trabajo completado y las actualizaciones de estado. Si un nodo permanece en silencio durante más tiempo que ese intervalo, el nodo maestro (similar al servidor maestro en el sistema de archivos de Google ) registra el nodo como muerto y envía el trabajo asignado al nodo a otros nodos. Las operaciones individuales utilizan operaciones atómicas para nombrar las salidas de archivos como una verificación para garantizar que no se estén ejecutando subprocesos paralelos en conflicto. Cuando se cambia el nombre de los archivos, también es posible copiarlos con otro nombre además del nombre de la tarea (lo que permite efectos secundarios ).
Las operaciones de reducción funcionan de forma muy parecida. Debido a sus propiedades inferiores con respecto a las operaciones paralelas, el nodo maestro intenta programar operaciones de reducción en el mismo nodo o en el mismo bastidor que el nodo que contiene los datos en los que se está operando. Esta propiedad es deseable ya que conserva el ancho de banda en toda la red troncal del centro de datos.
Las implementaciones no son necesariamente muy confiables. Por ejemplo, en versiones anteriores de Hadoop , NameNode era un punto único de falla para el sistema de archivos distribuido. Las versiones posteriores de Hadoop tienen alta disponibilidad con una conmutación por error activa/pasiva para el "NameNode".
MapReduce es útil en una amplia gama de aplicaciones, incluida la búsqueda distribuida basada en patrones, la clasificación distribuida, la inversión de gráficos de enlaces web, la descomposición de valores singulares, [24] estadísticas de registros de acceso web, la construcción de índices invertidos , la agrupación de documentos , el aprendizaje automático , [25 ] y traducción automática estadística . Además, el modelo MapReduce se ha adaptado a varios entornos informáticos, como sistemas multinúcleo y de muchos núcleos, [26] [27] [28] grids de escritorio, [29] multiclúster, [30] entornos informáticos voluntarios, [31 ] entornos dinámicos de nube, [32] entornos móviles, [33] y entornos informáticos de alto rendimiento. [34]
En Google, se utilizó MapReduce para regenerar completamente el índice de Google de la World Wide Web . Reemplazó a los antiguos programas ad hoc que actualizaban el índice y ejecutaban los distintos análisis. [35] Desde entonces, el desarrollo en Google ha pasado a tecnologías como Percolator, FlumeJava [36] y MillWheel que ofrecen operación de transmisión y actualizaciones en lugar de procesamiento por lotes, para permitir la integración de resultados de búsqueda "en vivo" sin reconstruir el índice completo. [37]
Las entradas y salidas estables de MapReduce generalmente se almacenan en un sistema de archivos distribuido . Los datos transitorios generalmente se almacenan en el disco local y los reductores los recuperan de forma remota.
David DeWitt y Michael Stonebraker , científicos informáticos especializados en bases de datos paralelas y arquitecturas sin compartir , han criticado la variedad de problemas para los que se puede utilizar MapReduce. [38] Calificaron su interfaz de nivel demasiado bajo y cuestionaron si realmente representa el cambio de paradigma que sus defensores han afirmado que es. [39] Cuestionaron las afirmaciones de novedad de los defensores de MapReduce, citando a Teradata como un ejemplo de estado de la técnica que ha existido durante más de dos décadas. También compararon a los programadores de MapReduce con los programadores de CODASYL , señalando que ambos "escriben en un lenguaje de bajo nivel y realizan manipulación de registros de bajo nivel". [39] El uso de archivos de entrada por parte de MapReduce y la falta de soporte de esquemas impiden las mejoras de rendimiento habilitadas por características comunes del sistema de bases de datos, como árboles B y particiones hash , aunque proyectos como Pig (o PigLatin) , Sawzall , Apache Hive , [40] HBase [41] y Bigtable [41] [42] están abordando algunos de estos problemas.
Greg Jorgensen escribió un artículo rechazando estos puntos de vista. [43] Jorgensen afirma que todo el análisis de DeWitt y Stonebraker es infundado ya que MapReduce nunca fue diseñado ni tuvo la intención de ser utilizado como una base de datos.
Posteriormente, DeWitt y Stonebraker publicaron un estudio comparativo detallado en 2009 comparando el rendimiento de los enfoques MapReduce y RDBMS de Hadoop en varios problemas específicos. [44] Concluyeron que las bases de datos relacionales ofrecen ventajas reales para muchos tipos de uso de datos, especialmente en procesamientos complejos o cuando los datos se utilizan en toda una empresa, pero que MapReduce puede ser más fácil de adoptar para los usuarios para tareas de procesamiento simples o únicas. .
El paradigma de programación MapReduce también se describió en la tesis de 1985 de Danny Hillis [45] destinada a su uso en Connection Machine , donde se llamaba "xapping/reduction" [46] y dependía del hardware especial de esa máquina para acelerar tanto el mapeo como la reducción. . El dialecto utilizado finalmente para Connection Machine, el StarLisp de 1986 , tenía paralelo *map
y reduce!!
, [47] que a su vez se basó en el Common Lisp de 1984 , que no tenía paralelo map
y reduce
estaba integrado. [48] El enfoque en forma de árbol que el La arquitectura de hipercubo que utiliza Connection Machine para ejecutarse reduce
en el tiempo [49] es efectivamente la misma que el enfoque mencionado en el documento de Google como trabajo anterior. [3] : 11
En 2010, Google obtuvo lo que se describe como una patente sobre MapReduce. La patente, presentada en 2004, puede cubrir el uso de MapReduce por parte de software de código abierto como Hadoop , CouchDB y otros. En Ars Technica , un editor reconoció el papel de Google en la popularización del concepto MapReduce, pero cuestionó si la patente era válida o novedosa. [50] [51] En 2013, como parte de su "Compromiso abierto de no afirmación de patentes (OPN)", Google se comprometió a utilizar la patente únicamente de forma defensiva. [52] [53] Se espera que la patente expire el 23 de diciembre de 2026. [54]
Las tareas de MapReduce deben escribirse como programas de flujo de datos acíclicos, es decir, un asignador sin estado seguido de un reductor sin estado, que son ejecutados por un programador de trabajos por lotes. Este paradigma dificulta las consultas repetidas de conjuntos de datos e impone limitaciones que se sienten en campos como el procesamiento de gráficos [55] donde los algoritmos iterativos que revisan un único conjunto de trabajo varias veces son la norma, así como en presencia de datos basados en disco . con alta latencia , incluso el campo del aprendizaje automático donde se requieren múltiples pases a través de los datos, aunque los algoritmos pueden tolerar el acceso en serie a los datos en cada paso. [56]
La implementación de MapReduce en MongoDB aparentemente tiene poco que ver con la reducción de mapas.
Porque, por lo que leí, es de un solo subproceso, mientras que map-reduce está destinado a usarse en forma muy paralela en un clúster.
... MongoDB MapReduce tiene un solo subproceso en un solo servidor...
"Realmente ya no utilizamos MapReduce" [Urs Hölzle, vicepresidente senior de infraestructura técnica de Google]
Apache Mahout [...] se está uniendo al éxodo lejos de MapReduce.
En octubre, Google ejecutaba alrededor de 3.000 trabajos informáticos por día a través de MapReduce, lo que representa miles de días-máquina, según una presentación de Dean.
Entre otras cosas, estas rutinas por lotes analizan las páginas web más recientes y actualizan los índices de Google.