Создание сложной сети подписчиков в твиттере, не достигая лимита API - PullRequest
0 голосов
/ 30 апреля 2020

Я хочу создать сложную сеть, узлы которой являются пользователями твиттера. Узел a будет указывать на узел b и c, если узел a следует после узла b и c. после этого я буду подключаться между узлом b и его последователями, а также между узлом c и его последователями. В конце я хочу получить огромную сложную сеть (скажем, около 1 000 000 узлов) фолловеров в твиттере. Есть одна проблема - я очень быстро достигаю лимита на твиттер, и мне нужно подождать. Есть ли способ сделать мой код более эффективным, чтобы я мог получить больше подписчиков, прежде чем мне нужно ждать достижения предела?

# import packages
import twitter
api = twitter.Api(consumer_key=".....",
                  consumer_secret=".....",
                  access_token_key="......",
                  access_token_secret=".......")
api.sleep_on_rate_limit = True
import math
import pandas as pd
import numpy as np
import pathlib
import queue
print(pathlib.Path().absolute())
print(pathlib.Path(__file__).parent.absolute())
plt.close('all')
# create dataframe

def getUserFromName(name, api):
    user_list = api.GetUsersSearch(term=name, page=1, count=1)
    if user_list:
        user = user_list[0]
    return user

def get_friend_list_by_user (user, api) :
    #getUserFromName(user,api)
    friends_lists = api.GetFriends(repr(user.id))
    #friends_lists = api.GetFriendsPaged(repr(user.id))

    return friends_lists

def update_E_and_V(E,V ,user,friends_lists) :
    for friend in friends_lists:
      if (friend.name) not in V:
       update_V(V,friend , E)
      update_E(E, user, friend)


def update_V(V: dict, friend , E) :
       details = [repr(friend.id) , friend.screen_name]
       V.update({friend.name : details } )
       E.update({friend.name : []})

def update_E(E, user, friend) :
        new_friend = [friend.name, repr(friend.id),  friend.screen_name]
        current_edges_list = E.get(user.name)
        if current_edges_list != [] :
            current_edges_list.append(new_friend)
        else:
            current_edges_list = [new_friend.copy()]
        updated_edge = {user.name: current_edges_list}
        E.update(updated_edge)

def create_E_and_V(name, upper_bound , E , V , api, friend_queue ) :
     if friend_queue.empty():
      user = getUserFromName(name, api)
      friend_list = get_friend_list_by_user(user, api)
      update_V(V, user, E)
      update_E_and_V(E, V, user, friend_list  )
      list(map(friend_queue.put, friend_list))
      counter = 0
     while  (len(V)< upper_bound) and not (friend_queue.empty()) and (counter < 10000) :
           user = friend_queue.queue[0]
           #time.sleep(5)
           friend_list = get_friend_list_by_user(user, api)
           list(map(friend_queue.put, friend_list))
           update_E_and_V(E, V, user, friend_list)
           user = friend_queue.get()
           counter = counter + 1
def dict_to_csv(d, csv_name):
    df = pd.DataFrame({key: pd.Series(value) for key, value in d.items()})
    df.to_csv(csv_name , encoding='utf-8', index=False)

import time
V = {}
E = {}
upper_bound = 20000
name = "Donald Trump"
friend_queue = queue.Queue()
for i in range(20):
 start = time.perf_counter()
 print("start ", i)
 create_E_and_V(name, upper_bound, E , V ,api , friend_queue )
 end =  start = time.perf_counter() - start
 print (i, "took", round(end/60,2), "min")
 print("end", i)
...