AspectJ:这段代码是什么意思?

时间:2015-11-25 12:04:42

标签: java syntax aop concurrentmodification

我刚刚开始面向方面编程,并且遇到了一个检查集合中并发修改的示例。但我在理解代码含义时遇到了问题: -

public aspect FailSafeIter {
    Map<Iterator,Collection> iterToColl = new HashMap<Iterator,Collection>();

    // Create interator
    after(Collection c) returning (Iterator i):
        call(* Collection.iterator()) && target(c)
    {
        iterToColl.put(i,c); 
    }

    // Update collection
    after(Collection c) returning:
        (call(* Collection.add(..)) || call(* Collection.remove(..)) ) && target(c)
    {
        iterToColl.values().remove(c);
    }

    // Iterate over collection
    before(Iterator i):
        call(* Iterator.*()) && target(i)
    {
        if(!iterToColl.containsKey(i))
            throw new ConcurrentModificationException();  
    }
}

任何人都可以解释上述行的含义以及它如何检测并发修改异常?

1 个答案:

答案 0 :(得分:0)

我刚刚修改了您的代码格式,并将注释更改为更具描述性,以便您了解正在发生的事情:

  • 第一个切入点捕获对Collection.iterator()的调用,即advice方法在内部键值映射iterToColl中记录所有新创建的迭代器及其对应的集合。这是该方面内部记账的第一步。
  • 第二个切入点捕获对Collection.add(..)Collection.remove(..)的调用,即调用修改集合的方法(这是一个警告,在迭代时不应该这样做)。如果找到一个调用,该通知将从内部映射中删除与此集合相关的所有键值对。
  • 第三个切入点有点模糊,因为它捕获对所有迭代器方法的调用,例如Iterator.next()(这可能是意图),也是Iterator.hasNext()等无害的方法(这里可能不需要)。如果拦截了这样的调用,则通知会检查是否在内部映射中找到了相关的迭代器。如果找到了,一切都很好,建议什么都不做。否则它会抛出ConcurrentModificationException,因为它假定在正在进行的迭代期间使用迭代器的集合已被修改。在后一种情况下,该集合将在上述第二个建议中早先从地图中删除。

总而言之,这方面非常神秘,只会在非常特殊的情况下工作(如果由于不精确的切入点而导致的话)。国际海事组织有很多选择让它破裂。但无论如何,这是一个有趣的想法,可能适用于简单明了的案例。不过,我还没有测试过。我只是在脑中使用AspectJ解析器来解决它。

我希望这个解释足够了。