From fbf5ffe67a63ddb43f003efeb6a1fc81bdf05ee0 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Ilkka=20Sepp=C3=A4l=C3=A4?= Date: Sat, 19 Aug 2017 10:00:18 +0300 Subject: [PATCH] #590 Add explanation for Adapter --- adapter/README.md | 82 +++++++++++++++++- adapter/etc/adapter.png | Bin 12086 -> 0 bytes adapter/etc/adapter.ucls | 70 --------------- adapter/etc/adapter.urm.puml | 37 -------- .../main/java/com/iluwatar/adapter/App.java | 14 +-- .../java/com/iluwatar/adapter/Captain.java | 27 +++--- .../com/iluwatar/adapter/FishingBoat.java | 9 +- ...shingBoat.java => FishingBoatAdapter.java} | 20 ++--- .../{BattleShip.java => RowingBoat.java} | 8 +- .../iluwatar/adapter/AdapterPatternTest.java | 29 +++---- pom.xml | 1 + 11 files changed, 121 insertions(+), 176 deletions(-) delete mode 100644 adapter/etc/adapter.png delete mode 100644 adapter/etc/adapter.ucls delete mode 100644 adapter/etc/adapter.urm.puml rename adapter/src/main/java/com/iluwatar/adapter/{BattleFishingBoat.java => FishingBoatAdapter.java} (70%) rename adapter/src/main/java/com/iluwatar/adapter/{BattleShip.java => RowingBoat.java} (92%) diff --git a/adapter/README.md b/adapter/README.md index 4059ea8522f..6de04a72c58 100644 --- a/adapter/README.md +++ b/adapter/README.md @@ -19,10 +19,85 @@ Convert the interface of a class into another interface the clients expect. Adapter lets classes work together that couldn't otherwise because of incompatible interfaces. -![alt text](./etc/adapter.png "Adapter") +## Explanation -## General usage of Adapter Pattern: -+ Wrappers used to adopt 3rd parties libraries and frameworks - most of the applications using third party libraries use adapters as a middle layer between the application and the 3rd party library to decouple the application from the library. If another library has to be used only an adapter for the new library is required without having to change the application code. +Real world example + +> Consider that you have some pictures in your memory card and you need to transfer them to your computer. In order to transfer them you need some kind of adapter that is compatible with your computer ports so that you can attach memory card to your computer. In this case card reader is an adapter. +> Another example would be the famous power adapter; a three legged plug can't be connected to a two pronged outlet, it needs to use a power adapter that makes it compatible with the two pronged outlet. +> Yet another example would be a translator translating words spoken by one person to another + +In plain words + +> Adapter pattern lets you wrap an otherwise incompatible object in an adapter to make it compatible with another class. + +Wikipedia says + +> In software engineering, the adapter pattern is a software design pattern that allows the interface of an existing class to be used as another interface. It is often used to make existing classes work with others without modifying their source code. + +**Programmatic Example** + +Consider a captain that can only use rowing boats and cannot sail at all. + +First we have interfaces `RowingBoat` and `FishingBoat` + +``` +public interface RowingBoat { + void row(); +} + +public class FishingBoat { + private static final Logger LOGGER = LoggerFactory.getLogger(FishingBoat.class); + public void sail() { + LOGGER.info("The fishing boat is sailing"); + } +} +``` + +And captain expects an implementation of `RowingBoat` interface to be able to move + +``` +public class Captain implements RowingBoat { + + private RowingBoat rowingBoat; + + public Captain(RowingBoat rowingBoat) { + this.rowingBoat = rowingBoat; + } + + @Override + public void row() { + rowingBoat.row(); + } +} +``` + +Now let's say the pirates are coming and our captain needs to escape but there is only fishing boat available. We need to create an adapter that allows the captain to operate the fishing boat with his rowing boat skills. + +``` +public class FishingBoatAdapter implements RowingBoat { + + private static final Logger LOGGER = LoggerFactory.getLogger(FishingBoatAdapter.class); + + private FishingBoat boat; + + public FishingBoatAdapter() { + boat = new FishingBoat(); + } + + @Override + public void row() { + boat.sail(); + } +} +``` + +And now the `Captain` can use the `FishingBoat` to escape the pirates. + +``` +Captain captain = new Captain(new FishingBoatAdapter()); +captain.row(); +``` ## Applicability Use the Adapter pattern when @@ -30,6 +105,7 @@ Use the Adapter pattern when * you want to use an existing class, and its interface does not match the one you need * you want to create a reusable class that cooperates with unrelated or unforeseen classes, that is, classes that don't necessarily have compatible interfaces * you need to use several existing subclasses, but it's impractical to adapt their interface by subclassing every one. An object adapter can adapt the interface of its parent class. +* most of the applications using third party libraries use adapters as a middle layer between the application and the 3rd party library to decouple the application from the library. If another library has to be used only an adapter for the new library is required without having to change the application code. ## Consequences: Class and object adapters have different trade-offs. A class adapter diff --git a/adapter/etc/adapter.png b/adapter/etc/adapter.png deleted file mode 100644 index f43358b042e73edcbcb9589e540a8d306fa1d6c1..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 12086 zcmbt)bzGGFw(lTHqap|bDk3p}bmtICg98H6pmZZ$4k<`Tmq-lVA>HswH`3AqA~_&1 zLkxAFfp_nH&bj-ZTl3d^e)Bx*w|afoS`(u3QkIy2iU0%x5zEWHcm)F8-~)lMgz#-Bb@voRs_mzT6G^+eI?@$YQu`lIznx-Py2ckby-GM{SKPK>;1Osf z46oOVd|%JW`DUhro>Z#itL4{~zy~5xT=>bfFOt4xByzESn~U1|CYX%1H>z__RFK+I zt15={W|DkWW2Hbt5&o$u7zueZ-YP* zd-X@cK298mIwxllkZ;;Cn%?Mj-T}W^u=Yo4P8g) z6Lbp~#yt+a!X&sJn-K)TlK3VGC*nimg9u&+!f<|6T`tH4&FHG#UJZ`VmdWGVg|vEPI2s%n38sj^j+9^ard6DLJT zgx$Sk3i)*y-T7RV)t+#v`fO-~?cz4>gt{fO?-dsW+0gkDg?EJ{cB&}((2KO7>f};Z zj~UXMjBlQCBvx-}=8=&A!2{gU*S;qmGmUF11^BmQq@rV{@=)LqT zxY$X-cw9#;Pj&zf0#&5HLI2YFwF`~d>_M9h>o+(q7xdUvLTHQU_f}cPyBCW^@<@bD z*u2nWdPO2hPHXaqN=$QYyHG}n+&*vGX}avJ&uB7R{p$6n^Umh2X%-5kajt4DzjJr9 zTDIm_eg?zMN@^A-qEp@}Y8MAVa&jJ;D?}5S2RO$m!@qv|6ctT1M3zDvgpD@IC*gk8 zp5$No?VSW*6)71jLA7`M4{igdlIf8nHYXUuX~zQWheuf;?~!W~FYwG!q;fEO)@?tH z2;qmDLOkjRp|tw&X`DoEB^EQPR@!Z6dk$KsYjTzC8^7Cn{*k7n0=PK@`C#z$lC zq)s59!O2#oYzM1C!*_H2Jv=>C z)fj3N@0NnxCrJD>pjk@ii#Ykw9(P!12_0!ISO+%xTgB|+W->Ghx$zsEcRK|=cQ)#V zc;t;*3tRMD8FAWeVM_3+ZV^7;Z(p7t7Io?oFMB#fe)*+QuU4K_0KDm)WjI@q8y7%O zx@sV<`g-_sD^vh5?bD&Sw+!Li1<;ELQMW`Rr2KhYx`{Bwy#U>nBk%)q)6u*lv%}rw z`OEQ>yv~J|%j7#$P}pP*2Sfl>Z@xq3I@XJw896WH*ha4(R$F>eAD`kcY;udr@`9{6 zArCsaSyOn+hm$EAu<+PXQjG0r4->3HGo(pe$_oZPViwzt{A>D+R-8PXUEF&aG}Emd&r-|vqi|+k*wkA;c;)k^8Am}qXwPKizfQP z57~?GY(jJkWMfJSu9S6bt}t>HuJZ5?kGwX@`*&J53+)$v2%=6-4L#SF5^3)Hbnb_P z?|APQd382^yBHO7ztHQmx8c|K8<}gJLTp1I3`j;tKr~(jhg`BgjA*^c0%Q4c@Z&nG z#chPZ`=g)4;5(tMM%q;$ItplF%XX9A0!|*cs>B?z1UT~khFW*Sceis=w+IOL#fJSH z>&3z-mEh%L^vw`?Snk>OS?fTm;H74GrP`@s(^?HhXN5)YJn1`rCf1yBu+2L1ghU!y^q#~_ z+Mg+1g-hS(BRZMUU1cCYy|xyx&cl<9q%O3lH2vH${p8VghEi@d?>nWqT=Z+sqY)bQ zZb3yfrG{N1eWd#Z9$SRDNz>%{sDM3J!{caZ6B8;&!70R!x2`YVI8sUyak%hnByXL0 zulz%85iRRQXWv|7Rf{Kbp;=aC#x8h%KQ$_jF%Ik1OA^aOw?d&v`5tt3e?X}`qot1> z%sjn(eg#J}g_!?7vR4HVH+PX|RS|c{`y!WS4z@)(yB*%NzwC9`&!KcC@p*j(d1o{B zvd*6$+hq78_OKVXdPJE+mvA+TXj6?zl3@rZneaLrkL@Nop8nX-EfsRvO3SlvKr_ER zlo=8|g&r!7cppq0;2uKOkdc??^1YyGMfirWvF#!+*|6+IT7JJK2uPm8 z=d=`Yd2)s@UbNnZnO$DG&n)yzk6p4RNQZq5IDIM3v$fEcH}vu$*LQQ@ZR-oNrFI9+ z8%g4lrN2s{3-(Rk#Jsx-Zkp~Xa1-#%P%wwPs#KbIJ&S2?(2tk3d0MXA&BF1MO~Ww| zxf3jHo4nI!u>};CG`}{({q;V^O=Hc8?le?xP zKk5iP1$Cx;g3bIi$MnQ8#hH0n+%3E7Pcf6@MaQ`pr=H^^SlWI@*-g((+>)svu~_Va zJQLOHDKu*}Sd%^+}_C1{LKEF>)=G21g<@JJ~c#Z-a~8jgiOG-js%RdH>1Q9 z%8em1TB*}A*x^C|$Gq2{Vr!0&1Yg1XlQ@c?ph`($0v?|VtCzLU5Aw*+zm%*S+P+p! zH*<2Umd$1mhsOail=Q9Ue5I#qk(^ zPmk+Za%m#<<3q$^LKC-oo&#grgmBeWS(j_0K|oC#J{~(j!Z3THM~a7}6eGBfUV;2ZZP`9mZZFt8c0Qwp;n zHPJ_B^!Q0fTiT-dexA>t_-6*^k+qIT-mHNn++z)`g);^SGqMe1yfr*JUkQ}2A?*QPM4k~ViG+PO>awo zNebGU!lNYEr>Ll_6XfHohMgWpM@Rq3CV;g~zY)CR>AB=-U~zHr2e5`{$Own%0BED< z4?1mM$xABirLd*g+JpE=?x+aXT`fbIq70~{r#G$9E0=>of!W7t|F|m~?Yz5eOe5qv zXu4<_92oKYBDhqrzJhnQxV~54Q>PfOvt%{rj744ym8tC~)n!#=U|({$K5i!rn+tql z?E;oStR*+P!S9OAA`VBgWIGMZce=&Bf2w6=9UL5FMp`&)fMeViVMpk#vR34%A{Y!F z$-5^)9T)ln?L5B-+o;(U@HyUDgg9Jql|M01(EW);;yN+7wfeHaY~GG^uwm++ zdzZn~v_kJ(ibWs7(Xp~r2tUn99KYZ676B!GoY^WEY!gmG=!2B46}7h)JXMgUwEVJq=1UK4s!Bb-Ej2nG?)*!66?QM7pPPuX zaDhH)tPT+Y(QYfR*pK~vzgpyF8Q%Hb${e_}fQ4z=mYfr-spJ!fow5#;;<&4`-FDdJtoyc{Hok(A2E_B}M5YoQ`z#YYr{7sc(^K82Y zdHb$0MR=xg7PNg7OcI6wdrwYIesE`H4KAyyY-(bC(P=4d6eHP=TDC4xlsF=0?&XYe{i$FuI2 zP4Bm(6C*Sfi?*jqijbg}=fSb~=B{iVM^s}=uzQryJyP>I$4c6V}^d@Cnjeg}XR!R>$3P2xb*QmU8- zUyt_B2N(>#E-UJv?g1bo`&E(*&Kt4#6cG^-9{#A>LYKbRo@_w9U~6o*?CbO*@dt>c zkX#;ge3-47gnPN1hTT9*>nqA~d^tujWq?F=v5;LYXSCak$T$-rF8Nm6`K=h^2TK464&o@@95SN8#v)TOL6x3PB#fcfwHyM1Xg0(A@wB81iMnHFxZBYPX?)|AtlrlI~e217Ud8;O`0+MQnv&B*EMIP@@U{xj2O zel@l1j(B8L$jirPx<;>OXjt1>!1D%RfCKhwpB3E8Z&|XccpH6FgSLIk%VT^PrIyz1 zQ+mX_BelPn-!4Ws#WvR7_JJs{y1E+3?9c=o=89;5f<ZTS= zHL%7ve&Vt>#ULB7=}9|Jfc|&-VCD8 zo_W>C^Q02v!%)q|hKBAlOd05xavn09X!fx6PCLoRlQ= z{`l+NLd0xsSl1&F*WlGG*~p>6!4S8p$w^1#(0GdX&(_(opNLCaJ-N8Mg~1W3D7O^} z_$$F#UtF?*Y(OZ~QQ}Aboc9WI=Op%u6NosPuC{|bf(4p#AhVgsua5zSf}Q%VZ)0{=Im*yX;_*R+{HJ>A-cl#&ljJXyHc z*KtLI%RB-Q21WsXvoaCF<53G_&xPuM?62OW^l}5>5h%=$Lc#!y4bEM~l zl-lR%3^jCSW`|_T9Ey)GG@8>G=0@@qgs9btfG(?Fz=Zx%vOkuA>kcUo50|uJ#mP=d zVo`!9DhkfBuC`aSl?jcy4LtZvr|0`cx~bt~C050IJNln9w%&(6F)f2OZ>^bGo9375 z@|p)!{EZbmQka2bg-C{R-O7@NOVOZL$k&(O-Gqv^0JMi8hH05LmE_|JM!kx44O9-4 zSUg_wCaLvl=u-eAwZHM2s<}d@Qat`ETMuSA-arQi1@-^(t4|UO>AITITRj)+()*PS z?7+<8K`unT+L}*3B=gkXZbWyZn0+$Bb_bya^x-d3nM1fWx^n!93|yVwOE7=Z?b~d? zz+e6IId!{2W>j`ccr*IWQ|!IeBE4`5Sl{Q*JUMQ;eHLq~VGBCBWL<2QF8Tnljc)KR zWyHg=BX~8;P@rD=6x)NMne92>!nS?)Q$Q?l`b1zp;og67vA<0W2xDR(E}&k)@17*` z9>%eoS({VXl{|mNP{-ETpOWJV7tDN52IZvr+|=B7hcC3@Q_UCI5nT^+f@DBLr15+Mh0@VZ(nrZ3?xf)^#EB0kuYM_EnvweD9f9xj%wsvv8K zCfqAqF_%&y3k=(V!9aTnJh{=*e%FAnoQeZOfE1Wve*1bxLJ~0Bd~Khy{HC5>JI3Xd8%Og%1#}x(~-rPEMNKZa(4p`^;#cm!JQ2 z+0?-TiSGbrVu~zKumL_m#fQQ4&-8V5`@P&i6_}Cf_dFH{G;#xov~o^9KA>vE9_@fk zFe6u>Suq0MdHYt9m6eSRF;o3)cOI(;2k^A#aFzg=_Hd(<{pleBfawEni6HK4Vtt$f z0s=xp8_l9t(Te~fnIQD9abc^Pn1r9yRqVcKrJ|O*G`Rpj+(1dKnYG5=np z#Eznzo)|_Haod>lY!+rfVGq#i#8p;R)>EZ9IXQZVxKEx}6vDR{RZEnsCO+iZk-tke zaVg+oB@4@d-Z%5~ME_Z8SIBbgypx`7qAp%bs%9glsVML{sl)%jG*H*GPH9`LC`jv{`Hs%Ps5# z>ec>&q_1C3vA10c#0A|V-iC;k#L(dOTU}i(C@5$;y75GDzX+aue!i+jbG3Hp?>o3a@j{88Guai|I71$74QmD2H=GHHiBnU6#}oRp_Lh0uHL2>m#bV+kD=Q1(Dze)Q>WSHez{5H*dIUPsPBNCO zv*k_Fnu34rdkTyIU$?cf`PEDT()I^>=5@8s2b7c<5ZbHE4tRdo@v-0uUAobgYJt5` z_nlX|wFa-SjqiRGk*y6FSo-al|ClHft56~wpG*Drd#ZE-z}0^@6M`rM0Od%KNWwu1 z!$9R99estdB-c8r#D=!EHYFuxFQ9&I9M}yeF>7nC4_1i#(x2dzN0+XZbbxa z(m>KTF(UlSqpn2?mkHSNQW3j)SWK+BuI@9&5C6jpXBRi)uipIU7um?it4CmrG$0Te z2@*dY$;!b|R#vtK7zd-wxU`Xx5!c4lzX_>${>!faf#U=KF!1vOT+8)EJo3>B!0Sj{ zfvI8?0H{0z@;2nIYTcLz_1G8GYMr5a1TKEM3TNRX#(mCdUaNId^v&-SFT$JJqAY(} z;y-HFqrg&mV)g5OkPA}1_qILLZanR?QN>qz9Je^UYr*7uAkNhTUu@a$y-tBYB3b!v$QAfG#t2E0(@ zLYX8;iOw&tw<5zj`t}~MMf5s0Me+9kM}Pw+g~FOR|b%65MF(V7pqiAC8mj6ZKZ z1rhvP=g7*-(|0%Dn9SR$KiuoeYvHe1D?bNz7{9!Gf_AUH1|0{G33rEzc<(sSD#i{k zz}5%e&UWmtc9)SN>S?NJMXq?hd!J9~@xW~`;4Yv350-**ai{72!2EvV-U(4PDysU+ z1)X>NI-)0Ap84sTOo;212$Ix%L^K0-X&KPBq$`h?Yz!ez>)}TR8m~PN6lG_qX}Y$( zvvSqe(aecFGV-~I_y8>rv!*<4=x<=z+>0+84#BBBzs(Xq=jomKaXnbAWRDw7R+9`* z5q`JnbfCCc-Pnvi=(KO%Td#LBB`0Bdl3*U3zbY6pMdELocR4?Rh^gV z(0EFYEa=-tE3?a%>2qkRj}Fq~Qh1L^Ju0V)(fAq?I@YL6opFbeWF|W{RArLHN z*cJO-mvW>6-s9_PKh=+(%2jvuudDs&aDIOjQhr_{B0hHv9YIvXTTcSVWLr)=r?7n* z_m)aZM2-gecRVk&p28dl(}oToBas_-V!T9fHMj1d*?iHH))y0mA5M%+-#7sKsxzr(wSKelmo(kq@6KJQf2 zaMSz@NbzLV-_N~ZL}n|DlzS`Pk6Xo0NLqDPOp(konUKA|G)~RzTbCMf?FBtl0P2|x zPhLK+EsZ70kpgBB>9h~|&<_S=ZnJnr(wwgb@0HEHO2T-$vC*8F}V1K+mq+EjM;uai!WUFDR({Cw3o%waHaIsVqhe^WUA8oPI$tt7^KfFgmD zmhj)DrRbczYVh{lQ)beMGIk=zu-{hJ=9wSR=kEys39w*PxfxJx9R*+)cKZ-dk{hh5lAe%cY&c9fA0`nCJ9T@Qy|N406Qei^^$@bTa{lc%Jch0?Uu} za^`1Z|JoyP{d1TxU*#12;q?(&Pppi`@O<+`Zm=|vv9m|PIIR<-c@wXj7jzI_)vlHB zY7?j$GIu`i)lTRiHq6#Z9{G=*lm1cVWK0FL7oA;Yjicmud*Nk+2x)o4IY%9Q`FCB# z>7Wd8KSm>#$dGS9;kwj8pTq|LM$sXn2y?!J*Lqwd=ZDM$Pe5DIR4Qw`?eO_8<~rSB zBG?VNK8XWB-uMx)?B@o>QuGf6h89{y|Fh{BRH_S3vbe@D&H*uyxSluUfBWh7hg1E@ zdp<|$?uqo5vN}kxN~jUT4Vc3EgFt5zU(tN`@dpa;Ht!p0n4 z;IZ~`5o|mKdHj1{t+8v)#vuvj=swNF6xKj0^alv>t$$X|PgWm8M3wl%F~?ZQTNoIn zu0a*vb$0f??h%Hk2{#ho4_D<^!_?GNT5i0jCphyJ259BCgn{TkU@CDT|J(Rw1xKPe z8mx4nBg%j#2NhpE!r3nkGJ2yfqJ+~bZsg%nF9wpuePd;1#e2We6){s`sz?lz0+O+R zKG!c!`eoD;f?DJ520|VJA9nU}Bww2O(#|Q;s`$|b-f>I+5 z=(mA+tV~vUMaAgG@R%@M>&L;V>;>{pi(_Ze<=*QZS=*k7w^3oBjsVE&{UDZ4nM(Y< zVzx+Gf$2WpgCaE}+M_IflWxv7X;92x`TQ8cWn^XVn^tUS!m~9F#NV|$f7)!slaP8a z@f(9RF*f`USQ9(^0{|{_l3z4*HoOSaXVNZz=cNusG>qo`xRn~4q+2~*F){fv&%~*1 z7zi0)X5U_wxfQFqQZQd>SjJAfEQVO>Gz^CH&ic)mA6X&aK){ zMuV#UcBdb7tsN$Jr{lx%HN9cyUk#vDIwFmB>FcqLthb$i(q)rdtL;Fv&S#aiCpvUV zZISp-9!-Z^WpyVT)c%ozPK1nnj=2*{_|dRTEZ4EoU6DyG;ULe;8z~@=lIHpLB-rG*e@xmHz`?9BC>LB&Ziw>#p~F>Dhxdl7a4HdnfAD!e|07b*1aT*uD5XZ8=@e@!o`8iRrmG2{wh{jd?q)W+FS5D)Vk&$Uv1Ir=rmx=8xO2=zlRM|{>83EGE)53kwkTuclii}mH3IVMcJAGR7!Q-bp7Ae&i^||Z#*W(7UwM3i4FQfjApY- zh*iD@)7M2-mAsgj|F1;WweOpkSese^i$VQ=p?|4M1EVi;BG!?7SGD#i%MSN1rK6u0 z2Cbqe>c>yiUff^-J7lH|PwBoU^sP^JoGI}%UMKzQ&jV+5>Y>jR_Bm7&c2+=>zywuP zw^Y&vDe0#6TkdM4D<-$9CYLT)*N*Z7@!4+tRkb8h*dh}li`!USlH9NNcqzeFy|Dmj zVlqY9EOW}!>26V3XWaaTPmnHHx=#GL?bhqLxs!!Z{L1k=*LkH)B5UU5A4i{blc3T+ zucl?Hlc|6fv~TR52Gzk_yCNrzM(VS2$h7}2%)Up37l&%X)fxS(Gw|lB10kevejMn3 zRnro(M}Jt=fwa_JN`tq&guzL+uHZ$x+B7=aGVdRZ*X<1FdOp7a+%vwL?f7q%=*jQs zTe9kbSoKni;HPwFwhHWpjw{e_>gBUmk^#}jm$En(4+Pv?1{~vAM z|7Hg8U)-_lue8acQLPsRiLb_~F-{ERWnLt6A9p@)E{rbzcw4zfnh$`^{XeJtg?#fv*wk6Nemf6zEO%20Js?zs##=z zpAC)?m;wsK`G4u&ZRS1YiJ#szj5v}`!u0gO|Gr`VPyNC`g4dHEN(o@RaXr`q`9Af( e8snW@di29z4}QOi2mIL_BrpB)MXA&q|NjB?hv+8& diff --git a/adapter/etc/adapter.ucls b/adapter/etc/adapter.ucls deleted file mode 100644 index 290ff544e5a..00000000000 --- a/adapter/etc/adapter.ucls +++ /dev/null @@ -1,70 +0,0 @@ - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - \ No newline at end of file diff --git a/adapter/etc/adapter.urm.puml b/adapter/etc/adapter.urm.puml deleted file mode 100644 index 847427a449f..00000000000 --- a/adapter/etc/adapter.urm.puml +++ /dev/null @@ -1,37 +0,0 @@ -@startuml -package com.iluwatar.adapter { - class App { - + App() - + main(args : String[]) {static} - } - class BattleFishingBoat { - - LOGGER : Logger {static} - - boat : FishingBoat - + BattleFishingBoat() - + fire() - + move() - } - interface BattleShip { - + fire() {abstract} - + move() {abstract} - } - class Captain { - - battleship : BattleShip - + Captain() - + Captain(battleship : BattleShip) - + fire() - + move() - + setBattleship(battleship : BattleShip) - } - class FishingBoat { - - LOGGER : Logger {static} - + FishingBoat() - + fish() - + sail() - } -} -BattleFishingBoat --> "-boat" FishingBoat -Captain --> "-battleship" BattleShip -BattleFishingBoat ..|> BattleShip -Captain ..|> BattleShip -@enduml \ No newline at end of file diff --git a/adapter/src/main/java/com/iluwatar/adapter/App.java b/adapter/src/main/java/com/iluwatar/adapter/App.java index 239424da9cb..a624cc38f26 100644 --- a/adapter/src/main/java/com/iluwatar/adapter/App.java +++ b/adapter/src/main/java/com/iluwatar/adapter/App.java @@ -34,14 +34,14 @@ * object. This example uses the object adapter approach. * *

- * The Adapter ({@link BattleFishingBoat}) converts the interface of the adaptee class ( - * {@link FishingBoat}) into a suitable one expected by the client ( {@link BattleShip} ). + * The Adapter ({@link FishingBoatAdapter}) converts the interface of the adaptee class ( + * {@link FishingBoat}) into a suitable one expected by the client ( {@link RowingBoat} ). * *

* The story of this implementation is this.
- * Pirates are coming! we need a {@link BattleShip} to fight! We have a {@link FishingBoat} and our + * Pirates are coming! we need a {@link RowingBoat} to flee! We have a {@link FishingBoat} and our * captain. We have no time to make up a new ship! we need to reuse this {@link FishingBoat}. The - * captain needs a battleship which can fire and move. The spec is in {@link BattleShip}. We will + * captain needs a rowing boat which he can operate. The spec is in {@link RowingBoat}. We will * use the Adapter pattern to reuse {@link FishingBoat}. * */ @@ -53,8 +53,8 @@ public class App { * @param args command line args */ public static void main(String[] args) { - Captain captain = new Captain(new BattleFishingBoat()); - captain.move(); - captain.fire(); + // The captain can only operate rowing boats but with adapter he is able to use fishing boats as well + Captain captain = new Captain(new FishingBoatAdapter()); + captain.row(); } } diff --git a/adapter/src/main/java/com/iluwatar/adapter/Captain.java b/adapter/src/main/java/com/iluwatar/adapter/Captain.java index 6d88b1975dc..3690169800d 100644 --- a/adapter/src/main/java/com/iluwatar/adapter/Captain.java +++ b/adapter/src/main/java/com/iluwatar/adapter/Captain.java @@ -23,33 +23,26 @@ package com.iluwatar.adapter; /** - * The Captain uses {@link BattleShip} to fight.
+ * The Captain uses {@link RowingBoat} to sail.
* This is the client in the pattern. */ -public class Captain implements BattleShip { +public class Captain implements RowingBoat { - private BattleShip battleship; + private RowingBoat rowingBoat; - public Captain() { + public Captain() {} + public Captain(RowingBoat rowingBoat) { + this.rowingBoat = rowingBoat; } - public Captain(BattleShip battleship) { - this.battleship = battleship; - } - - public void setBattleship(BattleShip battleship) { - this.battleship = battleship; - } - - @Override - public void fire() { - battleship.fire(); + public void setRowingBoat(RowingBoat rowingBoat) { + this.rowingBoat = rowingBoat; } @Override - public void move() { - battleship.move(); + public void row() { + rowingBoat.row(); } } diff --git a/adapter/src/main/java/com/iluwatar/adapter/FishingBoat.java b/adapter/src/main/java/com/iluwatar/adapter/FishingBoat.java index 2124d9d9fbe..c46814d18f1 100644 --- a/adapter/src/main/java/com/iluwatar/adapter/FishingBoat.java +++ b/adapter/src/main/java/com/iluwatar/adapter/FishingBoat.java @@ -27,7 +27,8 @@ /** * - * Device class (adaptee in the pattern). We want to reuse this class + * Device class (adaptee in the pattern). We want to reuse this class. + * Fishing boat moves by sailing. * */ public class FishingBoat { @@ -35,11 +36,7 @@ public class FishingBoat { private static final Logger LOGGER = LoggerFactory.getLogger(FishingBoat.class); public void sail() { - LOGGER.info("The Boat is moving to that place"); - } - - public void fish() { - LOGGER.info("fishing ..."); + LOGGER.info("The fishing boat is sailing"); } } diff --git a/adapter/src/main/java/com/iluwatar/adapter/BattleFishingBoat.java b/adapter/src/main/java/com/iluwatar/adapter/FishingBoatAdapter.java similarity index 70% rename from adapter/src/main/java/com/iluwatar/adapter/BattleFishingBoat.java rename to adapter/src/main/java/com/iluwatar/adapter/FishingBoatAdapter.java index 5e4da91f859..c94932b2b5f 100644 --- a/adapter/src/main/java/com/iluwatar/adapter/BattleFishingBoat.java +++ b/adapter/src/main/java/com/iluwatar/adapter/FishingBoatAdapter.java @@ -27,30 +27,22 @@ /** * - * Adapter class. Adapts the interface of the device ({@link FishingBoat}) into {@link BattleShip} - * interface expected by the client ({@link Captain}).
- * In this case we added a new function fire to suit the interface. We are reusing the - * {@link FishingBoat} without changing itself. The Adapter class can just map the functions of the - * Adaptee or add, delete features of the Adaptee. + * Adapter class. Adapts the interface of the device ({@link FishingBoat}) into {@link RowingBoat} + * interface expected by the client ({@link Captain}). * */ -public class BattleFishingBoat implements BattleShip { +public class FishingBoatAdapter implements RowingBoat { - private static final Logger LOGGER = LoggerFactory.getLogger(BattleFishingBoat.class); + private static final Logger LOGGER = LoggerFactory.getLogger(FishingBoatAdapter.class); private FishingBoat boat; - public BattleFishingBoat() { + public FishingBoatAdapter() { boat = new FishingBoat(); } @Override - public void fire() { - LOGGER.info("fire!"); - } - - @Override - public void move() { + public void row() { boat.sail(); } } diff --git a/adapter/src/main/java/com/iluwatar/adapter/BattleShip.java b/adapter/src/main/java/com/iluwatar/adapter/RowingBoat.java similarity index 92% rename from adapter/src/main/java/com/iluwatar/adapter/BattleShip.java rename to adapter/src/main/java/com/iluwatar/adapter/RowingBoat.java index 62ee366e759..a9ca9ad3971 100644 --- a/adapter/src/main/java/com/iluwatar/adapter/BattleShip.java +++ b/adapter/src/main/java/com/iluwatar/adapter/RowingBoat.java @@ -24,13 +24,11 @@ /** * The interface expected by the client.
- * A Battleship can fire and move. + * A rowing boat is rowed to move. * */ -public interface BattleShip { +public interface RowingBoat { - void fire(); - - void move(); + void row(); } diff --git a/adapter/src/test/java/com/iluwatar/adapter/AdapterPatternTest.java b/adapter/src/test/java/com/iluwatar/adapter/AdapterPatternTest.java index 89c9bc5d50f..9938f055963 100644 --- a/adapter/src/test/java/com/iluwatar/adapter/AdapterPatternTest.java +++ b/adapter/src/test/java/com/iluwatar/adapter/AdapterPatternTest.java @@ -39,9 +39,9 @@ public class AdapterPatternTest { private Map beans; - private static final String BATTLESHIP_BEAN = "engineer"; + private static final String FISHING_BEAN = "fisher"; - private static final String CAPTAIN_BEAN = "captain"; + private static final String ROWING_BEAN = "captain"; /** * This method runs before the test execution and sets the bean objects in the beans Map. @@ -50,34 +50,29 @@ public class AdapterPatternTest { public void setup() { beans = new HashMap<>(); - BattleFishingBoat battleFishingBoat = spy(new BattleFishingBoat()); - beans.put(BATTLESHIP_BEAN, battleFishingBoat); + FishingBoatAdapter fishingBoatAdapter = spy(new FishingBoatAdapter()); + beans.put(FISHING_BEAN, fishingBoatAdapter); Captain captain = new Captain(); - captain.setBattleship((BattleFishingBoat) beans.get(BATTLESHIP_BEAN)); - beans.put(CAPTAIN_BEAN, captain); + captain.setRowingBoat((FishingBoatAdapter) beans.get(FISHING_BEAN)); + beans.put(ROWING_BEAN, captain); } /** - * This test asserts that when we use the move() method on a captain bean(client), it is - * internally calling move method on the battleship object. The Adapter ({@link BattleFishingBoat} + * This test asserts that when we use the row() method on a captain bean(client), it is + * internally calling sail method on the fishing boat object. The Adapter ({@link FishingBoatAdapter} * ) converts the interface of the target class ( {@link FishingBoat}) into a suitable one * expected by the client ({@link Captain} ). */ @Test public void testAdapter() { - BattleShip captain = (BattleShip) beans.get(CAPTAIN_BEAN); + RowingBoat captain = (RowingBoat) beans.get(ROWING_BEAN); // when captain moves - captain.move(); + captain.row(); // the captain internally calls the battleship object to move - BattleShip battleship = (BattleShip) beans.get(BATTLESHIP_BEAN); - verify(battleship).move(); - - // same with above with firing - captain.fire(); - verify(battleship).fire(); - + RowingBoat adapter = (RowingBoat) beans.get(FISHING_BEAN); + verify(adapter).row(); } } diff --git a/pom.xml b/pom.xml index 992537f9bce..347a6bc1516 100644 --- a/pom.xml +++ b/pom.xml @@ -466,6 +466,7 @@ abstract-factory builder prototype + adapter