繁体   English   中英

通过Twitter4J进行多线程Twitter访问

[英]Multithreaded Twitter access through Twitter4J

我编写了以下Java代码:

twitterStream.addListener(new StreamListener());

FilterQuery filterQuery = new FilterQuery();
filterQuery.follow(filteringUsers);
filterQuery.track(filteringWords);

twitterStream.filter(filterQuery);

跟踪Twitter中的某些用户和关键字(通过Streaming API)。 在这里, StreamListener是我对侦听器的个人实现。

我正在跟踪许多关键字,主题标签和用户,因此我在内存中积累了很多等待处理的推文。 实际上,我只是通过侦听器(在onStatus()方法中)将它们onStatus()并刷新到数据库中。

尽管如此,他们必须在内存中等待的事实显然会在几个小时内使内存饱和 在20分钟的运行中,我在内存中累积了177000个LinkedBlockingQueue LinkedBlockingQueue$Node对象和1.272MB的char[] (通过分析查看)。

我想保持管道连续运行,显然在当前状态下这是不可能的。

因此,我想知道是否有一种在多线程中添加多个侦听器的方法,以便它们可以同时清空推文队列并加快处理速度。

  1. 如果有可能:这些侦听器是否同时清空队列? 我的意思是:是否可能会出现他们多次阅读同一条Tweet的情况?
  2. 万一不可能:我该如何解决我的问题?

提前致谢。

尽管无法通过Twitter4J实现直接的多线程解决方案,但可以通过侦听器类决定模拟多线程队列处理。

假设StreamListenerStatusListener Twitter4J侦听器的专业化。

我们将队列复制到StreamListener ,作为私有属性:

private LinkedBlockingQueue<String> tweets;

队列在构造函数中初始化:

tweets = new LinkedBlockingQueue<String>();

此外,在构造函数中,我们构建了一个线程池,该线程池旨在从队列中(批量)读取推文并将其存储在数据库中:

    final ExecutorService executor = Executors.newFixedThreadPool(NUM_THREADS);
    Runnable tweetAnalyzer = defineMonitoringRunnable(tweetRepository);
    for (int i = 0; i < NUM_THREADS; i++) {
        executor.execute(tweetAnalyzer);
        try {
            Thread.sleep(THREADS_DELAY);
        } 
        catch (InterruptedException e) {
            e.printStackTrace();
        }
    }

可以按照以下方式构建Runnable对象:

private Runnable defineMonitoringRunnable(final TweetRepository tweetRepository) {
    return new Runnable() {

        @Override
        public void run() {
            List<String> tempTweets = new ArrayList<String>();

            while (true) {
                if (tweets.size() > 0) {
                    tempTweets.clear();
                    tweets.drainTo(tempTweets);

                    tweetRepository.insert(tempTweets);   
                }

                try {
                    Thread.sleep(TWEETS_SAVING_TIME);
                } 
                catch (InterruptedException ex) {
                    ex.printStackTrace();
                }

            }
        }
    };
}

TWEETS_SAVING_TIME是每个Thread对象在一次保存和另一次保存之间的等待时间)

最后,一旦tweet到达侦听器, onStatus()方法会将它们存储在队列中:

@Override
public void onStatus(Status status) {   
    tweets.add(TwitterObjectFactory.getRawJSON(status));
}

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM