Отправляет email-рассылки с помощью сервиса Sendsay
  Все выпуски  

Платформа Java - шаблоны, технологии, хитрости


выпуск 4

...

Xerox PARC подарила компьютерному миру очень многое. Если бы не близорукость руководства, то именно Xerox сейчас была бы на коне. В лабораториях этой компании готовились такие проекты, как Smalltalk, Dynabook. Но это дела дней давно прошедших. Сегодняшнее событие - AspectJ.

Аспектно-ориетированное программирование. AspectJ

Гради Буч - человек очень известный в мире программирования. Его книги, среди которых "ООП с примерами на C++" - бестселлеры. Этот человек придумал UML. Так вот, в одном из своих интервью он говорит о том, что C++ он сейчас использует редко (это уже известно давно), но то, что он использует AspectJ - это стало для меня сюрпризом. Если такой динозавр пишет на АОП языке, то мы - ящеры поменьше - должны, по меньшей мере, ознакомится с ним.

AspectJ - язык программирования, расширяющий Java и дающий ему возможности аспектно-ориентированного языка. Вероятно, это самый популярный АОП язык на сегодняшний день. Существует плагины для большинства распространенных IDE для Java, которые позволяют интегрировать AspectJ в них (NetBeans, Idea, Eclipse). На сайте www.eclipse.org вы сможете найти проект "AJDT", который добавляет все необходимые возможности в Eclipse. А так же, огромное количество полезной (главное понятной) документации. В Интернете на удивление много книг и других материалов об АОП, в общем, и о AspectJ в частности. Заинтересовавшиеся могут найти и почитать.

Я не буду описывать синтаксис и прочее (читай документацию, книжки). Нет, просто покажу 2 простых примера, прочитав которые, вы, возможно, не сможете устоять, и приступите к изучению AspectJ.

Первый пример:

Пусть мы имеем класс Person с полями name, email, address, которые должны быть не null.

      
class Person
{
 private String name = null;
 private String email = null;
 private String address = null;
 
 public Person (String name, String email, String address)
 {
  setName (name);
  setEmail (email);
  setAddress (address);
 }
 
 public void setName (String newName)
 {
  name = newName;
 }
 
 public void setEmail (String newEmail)
 {
  email = newEmail;
 }
 
 public void setAddress (String newAddress)
 {
  address = newAddress;
 }
 
 private static aspect NotNullValues
 {
  before (String newValue):
   call (void Person.set* (String)) && args (newValue)
  {
   if (newValue == null)
    throw new IllegalArgumentException ("message")6
  }
 }
}

Внутри класса объявлен аспект, который все попытки присвоить null хотя бы одному из полей пресекает, выбрасывая исключение.

Второй пример: Шаблон Singleton.

aspect SingletonAspect { private Hashtable hash = new Hashtable (); public interface Singleton {} public interface NonSingleton {} pointcut creationSingleton () : call(Singleton+.new(..)); pointcut creationNonSingleton () : call(NonSingleton+.new(..)); Object around (): creationSingleton () && ! creationNonSingleton () { Class s = thisJoinPoint.getSignature ().getDeclaringType (); synchronized (hash) { if (hash.get (s) == null) hash.put (s, proceed ( )); } return hash.get (s); } } Что делает этот аспект. Он по-человечески реализует Singleton. Как мы делали в Java? Мы писали private конструкторы, писали getInstance методы для всех конструкторов и так для каждого класса. Здесь же ОДИН аспект и всё. Рассмотрим 2 класса, использующие данный аспект:

class A implements SingletonAspect.Singleton
{
 ...
}

class B extends A implements SingletonAspect.NonSingleton
{
 ...
}

new A () == new A () //true
new B () == new B () //false

Всё, что необходимо сделать - пометить интрефейсом-маркером классы singleton и соответственно интерфейсом-маркером классы, наследующие он singleton, но которые не должны быть singleton. Это превосходно!

2006

В избранное