Аспектно-оријентисано програмирање

У рачунарству, аспектно-оријентисано програмирање (АОП) је патентирана[1] парадигма програмирања која има за циљ да повећа модуларност дозвољавајући издвајање механизмом крос-сечење проблема. То чини додавањем додатног понашања на постојећем коду без мењања самог кода, уместо одвојено наводећи који код је модификован преко "поинткат" спецификације, као што су "лог све функције позива када име функција почиње са 'сет' ". Ово омогућава понашања која нису у средишту пословне логике (као што улоговање) да се дода у програму без пренатрпавања језгра кода на функционалности. АОП формира основу за аспектно оријентисан развој софтвера.

АОП обухвата методе и алате који подржавају модуларизацију забринутости на нивоу изворног кода за програмирање, док се  "аспект оријентисан развој софтвера" односи на читаве инжењерске дисциплине.

Аспект-оријентисано програмирање подразумева разбијање програмске логике у различитим деловима (тзв. бриге, уједињене области функционалности). Скоро све програмске парадигме подржавају одређени ниво груписања и енкапсулације забринутости у посебне, независне ентитете пружајући апстракције (нпр. функције, процедуре, модули, класе, методе) које могу да се користе за спровођење, апстракција и компоновања ових проблема. Неки проблеми "пресецају" више апстракције у програму, и пркоси овом облику имплементације. Ови проблеми се називају укрштена забринутост или хоризонтална забринутост.

Пријављивање илуструје попречно сечење забринутости зато што стратегија пријављивања нужно утиче на сваки пријављени део система. Пријављивање на тај начин пресеца све пријављене класе и методе.

Све АОП имплементације имају неке прожимајуће изразе који енкапсулирају сваку забринутост на једном месту. Разлика између имплементације лежи у моћи, сигурности и употребљивости конструкције предвиђених. На пример, пресретачи који уређују начин да пресретну изразе ограниченог облика прожимајућег, без много подршке типа безбедности или отклањања грешака. АспектЈ има велики број таквих израза и сажима их у специјално одељење, један аспект. На пример, један аспект може променити понашање основног кода (нон-аспект део програма) применом савета (додатна понашања) на различитим придружењем поена (тачака у програму) наведеним у квантификацији или упитима који се зову "поинткат" (да детектује да ли је дати придружити тачка матцхес). Један аспект такође може да направи бинарне-компатибилне структурне промене на другим класама, као додавање чланова или родитеља.

Историја

АОП има неколико директних претходнице А1 и А2: рефлексија и метаобјектни протоколи,  субјектно-оријентисано програмирање, састав филтера и адаптивно програмирање. [2]

Gregor Kiczales и његове колеге у Xerox PARC су развили експлицитни концепт АОП, а затим ово са АспектЈ АОП проширење на Јави. Истраживачки тим IBM води приступ алата преко приступа дизајна језика и 2001. године предложио је Хипер / Ј и забринутост манипулације окружења, који нису видели широку примену. Примери у овом чланку користе аспектЈ јер је најпознатији АОП језик.

Microsoft Transaction Server се сматра да је прва велика примена АОП затим Enterprise JavaBeans [3][4]

Мотивација и основни појмови

Типично, аспект је расут или замршен као код, што отежава да се разуме и одржи. Расут је на основу функције (као што је пријављивање) која се простире на великом броју неповезаних функција које могу да користе своју функцију, вероватно у потпуности неповезаних система, различитим језицима извора, итд То значи да промењено пријављивање може захтевати мењање свих модула. Аспекти постају замршени не само са умереним функцијама система у којима су изражени него и међусобно. То значи промена једне бриге подразумева разумевање свих замршених забринутости или има нека средства којима се ефекат промена може закључити.

На пример, размотримо банкарску апликацију са концептуално веома једноставним начином за пребацивање у висини од једног рачуна на други:[5]

void transfer(Account fromAcc, Account toAcc, int amount) throws Exception {
  if (fromAcc.getBalance() < amount)
      throw new InsufficientFundsException();

  fromAcc.withdraw(amount);
  toAcc.deposit(amount);
}

Међутим, овај метод преноса превиђа одређена разматрања које би распоредило примену захтева: недостају безбедносне провере да проверите да ли садашњи корисник има овлашћење за обављање ове операције; трансакција (базе података) би требало да обухвати операцију како би се спречио случајни губитак података; за дијагностику, операција треба бити пријављена на евиденцију система, итд Верзија са свим тим новим проблемима, због примера, мога да донекле изгледа овако:

void transfer(Account fromAcc, Account toAcc, int amount, User user,
    Logger logger, Database database) throws Exception {
  logger.info("Transferring money...");
  
  if (!isUserAuthorised(user, fromAcc)) {
    logger.info("User has no permission.");
    throw new UnauthorisedUserException();
  }
  
  if (fromAcc.getBalance() < amount) {
    logger.info("Insufficient funds.");
    throw new InsufficientFundsException();
  }

  fromAcc.withdraw(amount);
  toAcc.deposit(amount);

  database.commitChanges();  // Atomic operation.

  logger.info("Transaction successful.");
}

У овом примеру други интереси су постали замршени са основним функцијама (понекад названа пословна логика забринутости). Трансакције, сигурност, и пријављивање свих примером укрштене забринутости.

Сада размотримо шта се дешава ако се изненада треба променити (на пример) и сигурносни аспекти за примену. У тренутној верзији програма, операције везане за безбедност изгледају разбацано преко бројних метода, а таква промена ће захтевати велике напоре.

АОП покушава да реши овај проблем тако што програмер да изразе укрштених забринутости у самосталном модулу под називом аспекти. Аспекти могу садржати савете (код се придружио одређеној тачки у програму) и интертипове декларације (структурни чланови се додају другим класама). На пример, безбедносни модул може укључивати савете који обављају безбедносну проверу пре него што приступите банковном  рачуну."Поинткат" дефинише време (придруже поена) када се може приступити банковном рачуну, а код у упутству тела дефинише како се спроводи провера безбедности. Даље, добар "поинткат" може да предвиди касније промене програма, тако да ако други програмер креира нови метод за приступ банковном рачуну, савет ће се примењивати на новом начину када извршава.

Тако, на горњем примеру спроводи се пријављивање у погледу:

aspect Logger {
  void Bank.transfer(Account fromAcc, Account toAcc, int amount, User user, Logger logger)  {
    logger.info("Transferring money...");
  }

  void Bank.getMoneyBack(User user, int transactionId, Logger logger)  {
    logger.info("User requested money back.");
  }

  // Other crosscutting code.
}

Једино могу да замислим АОП као алат за дебаговање или као корисник оруђа на нивоу. Савети треба да буду резервисани за случајеве где не могу да се функције мењају (ниво корисника) или не желите да промените функцију у производњи кода (дебаговање).

Модели придружене тачке

Компонента савет у вези једног аспекта оријентисаних језика дефинише се придруживањем тачки модела (ЈПМ). ЈПМ дефинише три ствари:

  1. Када се савет може покренути. То су придружени поени јер су поенеи у програму рада, где додатно понашање може бити корисно придружено. А придружена тачка треба да буде адресибилна и схватљива обичном програмеру да буде корисно. Такође би требало да буде стабилно преко неважних промена програма, како би један аспект требало да буде стабилан  преко таквих промена. Многе АОП имплементације подржавају метод погубљења и референце на терену као придружена тачка.
  2. Један од начина да одредите (или количина) придруживање бодова, зове се "поинткат". Поинткат утврђује да ли је дато придруже тачке утакмице. Најкориснији поинткат језици користе синтаксу као основни језик (на пример, АспектЈ користи Јава потписа) и омогућава поновну употребу кроз именовање и комбинације. 
  3. Средство за навођење кода да покрене придруживање тачке. АспецтЈ зове овај савет, а могу га покренути пре, после и око придруживања поена. Неке имплементације такође подржавају такве ствари које дефинишу метод у погледу на друге класе.

Тачка придруживања модела може се упоредити на основу придружене изложене тачкеж, како се придруже тачке су наведене, операције дозвољено на придружи поена, а структурних побољшања која се може изразити.

AspectJ придружена тачка модел

  • Придружене тачке  у аспектЈ укључују метод или конструктора позива или извршења, иницијализација класе или објекта, поље читају и пишу приступ изузетака сировина, итд Они не укључују петље, супер позиве, клаузуле, вишеструке изјаве, итд
  • Тачке пресека су наведене комбинацијом примитивних "поинткат" ознака (ПЦД).
ПЦДС одговара посебној врсти придружених тачака (нпр извршења метода) и има тенденцију да се уђе у Јаву као потпис. Један такав "поинткат" изгледа овако:
 execution(* set*(*))
Ако назив методе почиње сасети управо ту је један аргумент било које врсте.

"Динамика" ПЦД  проверава рунтиме врсте и везује варијабле. На пример,

  this(Point)
Ово сечење одговара када тренутно извршавање објекта је  инстанца класе Поен. Имајте на уму да неквалификовано име класе може да се користи преко Јаве нормалног типа проналажења.

Обим" ПЦДС ограничавају лексички обим придружене тачке. На пример:

 within(com.company.*)
Ово сечење било ком придруживању у било којој врсти у com.companyпакету.   * је један облик џокерске ознаке које се могу користити да одговарају многим стварима са једним потписом.

Тачка сечења може бити састављена и именована за поновну употребу. На пример:

pointcut set() : execution(* set*(*) ) && this(Point) && within(com.company.*);
Овај метод-извршења придружеје тачку, ако  назив метода почиње са "set" и this је инстанца типа Point у com.company пакету. Може се односи на употребу имена "set()".
  • Савет наводи да ради на (пре, после, или око) А Члан тачке (одређеног ) сигурног кода (наведено као код у метод). АОП Рунтиме позива савет аутоматски када поинткат одговара тачки да  се придружи. На пример:
after() : set() {
   Display.update();
}
То практично одређује: "ако set() поинткат одговара придружењу тачке, покрените кодDisplay.update() након што је придруже тачки завршења."

Други потенцијални модел придруживања тачке 

Постоје и друге врсте ЈПМс. Све инструкције језика се могу дефинисати у смислу њиховог ЈПМ. На пример, хипотетички језик аспект УМЛ могу имати следећу ЈПМ:

  • Јоин тачке су сви елементи модела.
  • Тачке сечења су неки изрази комбинујући елементе модела.
  • Средства која утичу на ове тачке су визуализација свих поклапања да се придружи тачки.

Међу-типови декларације

Међу-типови декларације обезбеђују начин да се изрази забринутост прожимајућег утицања на структуру модула. Познат и као отворена класа и проширења метода, ово омогућава програмерима да се изјасне на једном месту или члановима родитеља друге класе, обично у циљу комбинују све шифре које су повезане са бригом у једном аспекту. На пример, ако програмер реализује прожимајући екран ажурирања забринутости користећи посетилаца уместо тога, међу-типови декларације користећи образац посетилаца могу изгледати овако у аспектј:

  aspect DisplayUpdate {
    void Point.acceptVisitor(Visitor v) {
      v.visit(this);
    }
    // other crosscutting code...
  }

Овај фрагмент кода додаје acceptVisitor метод Point класе.

То је услов да свака структурна слика мора бити компатибилна  са оригиналним класама, тако да клијенти постојеће класе наставе да раде, осим ако примена за АОП може очекивати да контролише све клијенте у сваком тренутку.

Имплементација

АОП програми могу утицати на друге програме на два начина, у зависности од основних језика и окружења:

  1. комбиновани програм производа, важи у оригиналном језику и не разликује се од обичног програма до крајњег преводиоца
  2. крајњи тумач или окружење је ажурирано да разуме и имплементира АОП карактеристике.

Проблем промене окружења значи већина имплементација произвести компатибилне комбиноване програме кроз процес познат као ткање - посебан случај трансформације програма. Акпектни прегледач чита аспектно-оријентисане кодове и генерише одговарајуће објектно-оријентисане кодове са аспекта интегрисаних. Исто АОП језик може бити имплементиран кроз разне методе ткања, тако да семантику језика никада не треба схватити у смислу имплементације ткања. Само брзина начина спровођења и његова лакоћа размештања су погођени које методе комбинацији се користе.

Системи могу имплементирати извор нивоа ткања користећи препроцесоре (као C ++ је првобитно имплементиран у фронту) који захтевају приступ програму изворних фајлова. Међутим, Јава је добро дефинисана бинарним обликом који омогућава бајткод ткаље да ради са било којим Јава програмом у .class-file форми. Бајткод ткање може бити распоређено током процеса израде или, ако је ткање модел по-класи, током утовара класе. АспектЈ почео са извора на нивоу ткања у 2001. години, одржао је по својој класи бајткод прегледач  2002. године, и понудио напредна оптерећења времену подршку након интеграције AspectWerkz у 2005. години.

Свако решење које комбинује програме на рунтиме мора да обезбеди ставове који их раздвајају правилно одржавањем програмер је сегрегирани модел. Бајткод Јавина подршка за више изворних фајлова омогућава било које отклањање грешака на корак кроз правилно плетене .клас у изворном уреднику. Међутим, неки независни компајлери не могу да обраде ткани код јер очекују пруковање кода од стране Javac. (види "проблеми" испод).

Примена времена ткања нуди другачији приступ. То у основи значи пост-процесирање, али уместо крпљења генерисаних кодова, ово ткање приступа подкласи постојеће класе тако да се  модификације уводе према поступку-превасходни. Постојеће класе остају нетакнуте, чак и на рунтиме, и сви постојећи алати (Дебуггерс, Профилерс, итд) могу да се користе током развоја. Сличан приступ већ се доказао у реализацији многих Јава ЕЕ апликација сервера, као што су IBM's WebSphere. 

Терминологија

Стандардна терминологија која се користи у аспекту оријентисаног програмирања може укључивати:

Забринутост попречног извршења
Иако ће већина часова у току ОО модела обављати једну, специфичну функцију, они често деле заједничке, секундарне захтеве са другим класама. На пример, можемо желети да додамо евидентирање на наставу у оквиру података приступа слоја и да наставе у УИ слој кад год нит улази или излази. Даља забринутост може да се односе на сигурност, као што су контрола приступа и контроле протока информација. Иако свака класа има веома различиту основну функционалност, код потребан за обављање секундарне функционалност је често идентичан.
Савети
Ово је додатни код који желите да примените на ваш постојећи модел. У нашем примеру, то је код извршења који желимо да примењујемо кад год нит улази или излази. 
Тачка извршења
То је термин који даје до тачке извршења у апликацији у којој попречно сечење брига треба да се примени. У нашем примеру, тачка извршења је достигнута онда када  нит улази у поступак, а други тачка извршења је достигнута онда када нит излази  . 
Аспект
Комбинација тачке извршења и савет је назвао један аспект. У горњем примеру, додамо евидентирање аспекта нашој апликацији кроз дефинисање тачке извршења и даје исправан савет.


Поређење са другим програмским парадигмама

Аспекти изашли из објектно оријентисаног програмирања и рачунарског размишљања. АОП језици имају функционалност сличну, али више ограничену него метаобјект протокола. Аспекти се односе блиско са програмским концептима као што су предмети, микинс, и делегација. Други начини да се користе парадигме аспект-оријентисаног програмирања  укључује Филтере састава и приступ хипер деловима. Од најмање 1970, програмери су коришћењем облика пресретања и отпреме-шаром које личе на неке од метода имплементације за АОП, али то никада није имало семантику да је крст спецификације за сечење писмене на једном месту.

Дизајнери су сматрали алтернативне начине за постизање одвајања кода, као што су делимичне врсте у језику C#, али такви приступи немају квантитативни механизам који омогућава достизање неколико придружених тачака кода са једном декларативном изјавом.

Иако може изгледати неповезано, у тестирању, употреба руга или стуба захтева употребу АОП технике, као и око савета, и тако даље. Овде сарађују објекти за потребе теста, а попречно сечење забринутост. Тако су различити Мок Објекти оквири пружања ове функције. На пример, процес се позива на услугу да се биланс износи. У тесту процеса, где износ долази је небитно, само да процес користи равнотежу у складу са захтевима. 

Усвајање питања

Програмери треба да буду у стању да прочитауј код и разумеју шта се дешава у циљу спречавања грешке.[6] Чак и са правилним образовањем, разумевање попречне бриге за сечење може бити тешко без одговарајуће подршке за визуелизацију како статичке структуре тако и динамичног тока програма.[7] Почевши од 2002. године, АспектЈ почео је да обезбедђује ИДЕ додатке за подршку визуелизације попречних забринутости за сечење.

С обзиром на моћ АОП, ако програмер чини логичну грешку у изражавању попречног сечења, то може довести до широко распрострањеног програма неуспеха. Насупрот томе, други програмер може променити придружене тачке у програму - на пример, преименовањем или се креће методе - на начин који аспект писац није предвидео, са несагледивим последицама. Једна од предности модуларизације прожимајуће забринутости омогућује један програмер да  лако утиче на цео систем; Као резултат тога, таквих проблема садашњег као сукоба око надлежности између два или више програмера за дат неуспех. Међутим, решење за ове проблеме може бити много лакше у присуству АОП, јер само аспект треба да се промени, док одговарајући  проблеми без АОП могу бити много шири.

Критика

Прво, аспект оријентисано програмирање је патентирано, и на тај начин не слободно спроводиво.

Најосновнија критика ефекта АОП је да контрола протока је заклопљена, и не само гором него много оспораваном GOTO, али је у ствари тесно аналогно на шалу COME FROM изјаве. Очигледности примене, која је основа за многе дефиниције АОП (код у питању нема индикација да ће савет бити примењен, који је наведен), значи да савет није видљив, за разлику од изричите методе позива. [8][9] На пример, упоредите долазе из програма:[8]

 5 input x
10 print 'result is :'
15 print x

20 come from 10
25 x = x * x
30 return

са АОП фрагментима са аналогном семантиком:

main() {
    input x
    print(result(x))
}
input result(int x) { return x }
around(int x): call(result(int)) && args(x) {
    int temp = proceed(x)
    return temp * temp
}

Заиста, размак може зависити од рунтиме стања и стога не буде статично детерминистичка. Ово се може ублажити, али не решава статичке анализе и ИДЕ подршку пројекције која савете потенцијално подудара.

Општа критика јесте да за АОП тврди да побољша "како модуларност и структуру кода", али неки бројач да поткопава ове циљеве и онемогућава "независан развој и разумљивост програма".[10] Конкретно, квантификација од паузе модуларности: "мора, генерално, имати читав-програм знања да резонују о динамичном извршењу аспектно оријентисаног програма."[11] Даље, док њени циљеви (модуларност укрштених забринутости) су добро разумели, његова стварна дефиниција је нејасана и није јасно како се разликује од других добро успостављених техника.[10][10] Заиста, аспекти могу се пријавити на себи, што доводи до проблема као што је парадокс лажов.

Техничка критика укључује да је квантитативни "поинткат" (дефинишу где се извршавају савети) је "изузетно осетљив на промене у програму", који је познат као крхки проблем.[10] Проблеми се сматрају тврдоглавим: ако се замењује квантификација са експлицитним напоменама, уместо једног добија атрибут-оријентисано програмирање, што је једноставно експлицитан потпрограм позив и трпи идентичан проблем расејања који за АОП је дизајниран да реши.[10]

Имплементација

Следећи програмски језици су спроведени за АОП, у језику, или као спољна библиотека:

Види још

Референце

  1. ^ U.S. Patent 6,467,086
  2. ^ Lieberherr, Karl J. (1996). Adaptive Object Oriented Programming: The Demeter Approach with Propagation Patterns. PWS Publishing Company. ISBN 978-0-534-94602-9.  presents a well-worked version of essentially the same thing (Lieberherr subsequently recognized this and reframed his approach).
  3. ^ Don Box; Chris Sells (4. 11. 2002). Essential.NET: The common language runtimeНеопходна слободна регистрација. Addison-Wesley Professional. стр. 206. ISBN 978-0-201-73411-9. Приступљено 4. 10. 2011. 
  4. ^ Roman, Ed; Sriganesh, Rima Patel; Brose, Gerald (1. 1. 2005). Mastering Enterprise JavaBeans. John Wiley and Sons. стр. 285. ISBN 978-0-7645-8492-3. Приступљено 4. 10. 2011. 
  5. ^ Note: The examples in this article appear in a syntax that resembles that of the Java language.
  6. ^ Edsger Dijkstra, Notes on Structured Programming. стр. 1-2
  7. ^ AOP Considered Harmful (PDF). Архивирано из оригинала (PDF) 23. 03. 2016. г. Приступљено 24. 01. 2016. 
  8. ^ а б "AOP Considered Harmful Архивирано на сајту Wayback Machine (4. март 2016)", Constantinos Constantinides, Therapon Skotiniotis, Maximilian Störzer, European Interactive Workshop on Aspects in Software (EIWAS), Berlin, Germany, September 2004.
  9. ^ C2:ComeFrom
  10. ^ а б в г д Steimann, F. (2006).
  11. ^ "More Modular Reasoning for Aspect-Oriented Programs".
  12. ^ Numerous: Afterthought, LOOM.
  13. ^ „as3-commons-bytecode”. Архивирано из оригинала 03. 10. 2014. г. Приступљено 24. 01. 2016. 
  14. ^ Ada2012 Rationale
  15. ^ Several: AspectC++, FeatureC++, AspectC, AspeCt-oriented C Архивирано на сајту Wayback Machine (20. новембар 2008), Aspicere Архивирано 2012-07-21 на сајту Archive.today
  16. ^ „AspectCocoa”. Архивирано из оригинала 26. 10. 2007. г. Приступљено 24. 01. 2016. 
  17. ^ „ColdSpring”. Архивирано из оригинала 03. 08. 2012. г. Приступљено 24. 01. 2016. 
  18. ^ "Closer Project: AspectL."
  19. ^ "infra - Frameworks Integrados para Delphi - Google Project Hosting".
  20. ^ "meaop - MeSDK: MeObjects, MeRTTI, MeAOP - Delphi AOP(Aspect Oriented Programming), MeRemote, MeService.
  21. ^ "Google Project Hosting".
  22. ^ „RemObjects Cirrus”. Архивирано из оригинала 23. 01. 2012. г. Приступљено 24. 01. 2016. 
  23. ^ monad (functional programming) ("Monads As a theoretical basis for AOP".
  24. ^ Many: Advisable Архивирано на сајту Wayback Machine (4. јул 2008), Ajaxpect, jQuery AOP Plugin Архивирано на сајту Wayback Machine (13. јануар 2008), Aspectes Архивирано на сајту Wayback Machine (5. мај 2006), AspectJS, Cerny.js Архивирано на сајту Wayback Machine (27. јун 2007), Dojo Toolkit, Humax Web Framework, Joose, Prototype - Prototype Function#wrap, YUI 3 (Y.Do) Архивирано на сајту Wayback Machine (25. јануар 2011)
  25. ^ Using built-in support for categories (which allows the encapsulation of aspect code) and event-driven programming (which allows the definition of before and after event handlers).
  26. ^ "AspectLua" Архивирано на сајту Wayback Machine (17. јул 2015).
  27. ^ "MAKAO, re(verse)-engineering build systems" Архивирано 2012-07-24 на сајту Archive.today.
  28. ^ "McLab".
  29. ^ "AspectML - Aspect-oriented Functional Programming Language Research".
  30. ^ Adam Kennedy.
  31. ^ Several: PHP-AOP (AOP.io) Архивирано на сајту Wayback Machine (19. август 2014), Go! AOP framework, PHPaspect, Seasar.
  32. ^ „"Whirl". Архивирано из оригинала 20. 04. 2016. г. Приступљено 24. 01. 2016. 
  33. ^ "PLaneT Package Repository : PLaneT > dutchyn > aspectscheme.plt".
  34. ^ "AspectR README".
  35. ^ "AspectR - Simple aspect-oriented programming in Ruby".
  36. ^ Dean Wampler.
  37. ^ "gcao/aspector".
  38. ^ „AspectS”. Архивирано из оригинала 06. 01. 2006. г. Приступљено 24. 01. 2016. 
  39. ^ "MetaclassTalk: Reflection and Meta-Programming in Smalltalk" Архивирано на сајту Wayback Machine (29. јул 2015).
  40. ^ "aspectxml - An Aspect-Oriented XML Weaving Engine (AXLE) - Google Project Hosting".

Литература

Спољашње везе