Problema abstracto: Tengo un gráfico de aproximadamente 250,000 nodos y la conectividad promedio es de alrededor de 10. Encontrar las conexiones de un nodo es un proceso largo (10 segundos, por ejemplo). Guardar un nodo en la base de datos también toma alrededor de 10 segundos. Puedo verificar si un nodo ya está presente en el DB muy rápidamente. Permitiendo la concurrencia, pero no teniendo más de 10 solicitudes largas a la vez, ¿cómo atravesarías el gráfico para obtener la mayor cobertura más rápido?Buen algoritmo transversal gráfico
Problema concreto: Estoy tratando de raspar las páginas de un usuario de un sitio web. Para descubrir nuevos usuarios, voy a buscar la lista de amigos de usuarios ya conocidos. Ya he importado aproximadamente el 10% del gráfico, pero sigo atorado en ciclos o usando demasiada memoria recordando demasiados nodos.
Mi implementación actual:
def run() :
import_pool = ThreadPool(10)
user_pool = ThreadPool(1)
do_user("arcaneCoder", import_pool, user_pool)
def do_user(user, import_pool, user_pool) :
id = user
alias = models.Alias.get(id)
# if its been updates in the last 7 days
if alias and alias.modified + datetime.timedelta(days=7) > datetime.datetime.now() :
sys.stderr.write("Skipping: %s\n" % user)
else :
sys.stderr.write("Importing: %s\n" % user)
while import_pool.num_jobs() > 20 :
print "Too many queued jobs, sleeping"
time.sleep(15)
import_pool.add_job(alias_view.import_id, [id], lambda rv : sys.stderr.write("Done Importing %s\n" % user))
sys.stderr.write("Crawling: %s\n" % user)
users = crawl(id, 5)
if len(users) >= 2 :
for user in random.sample(users, 2) :
if (user_pool.num_jobs() < 100) :
user_pool.add_job(do_user, [user, import_pool, user_pool])
def crawl(id, limit=50) :
'''returns the first 'limit' friends of a user'''
*not relevant*
problemas de implementación actual:
- se queda atascado en camarillas que ya he importado, perdiendo así tiempo y los hilos son importadores de inactividad.
- Se agregarán más a medida que se señalen.
Por lo tanto, las mejoras marginales son bienvenidas, así como las reescrituras completas. ¡Gracias!
Cualquier relación con Robert Tarjan, el descubridor de varios algoritmos de teoría de gráficos notables (!)? –
:) Tristemente, solo la ciudad de Hungría de la que ambos obtuvimos nuestro apellido. Pero ambos amamos las computadoras y las matemáticas. –
No relacionado con la pregunta, pero tenga en cuenta que sys.stderr.write ("... \ n") se puede reemplazar por print >> sys.stderr, "..." (sin necesidad de "\ n", y use de la declaración de impresión más habitual). – EOL