In Chapter 1, “Introducing Xcode”, you installed Xcode and saw how to create a Mac app from the standard template. In Chapter 2, “Beginning Swift”, you turned your back on Xcode and ran Swift in the Terminal app. You learned about data types, variables, constants and collections.
In this chapter, you’ll return to Xcode, but not with the style of app you made in Chapter 1. This time, you’ll create a command line tool. This is an app without a graphical user interface that runs in Terminal.
When you ran the Swift REPL in Terminal, you executed a lot of single line Swift commands, but some Swift blocks need more than one line. It’s easier to edit and follow these in Xcode.
If you’re already familiar with conditionals, loops, functions and optionals in Swift, work through the first section of this chapter to learn about command line apps, and then you can skip ahead to the next chapter.
Creating the App
Start Xcode like you did in Chapter 1. If you see the “Welcome to Xcode” window, click Create New Project…. If you don’t see that window, go to File ▸ New ▸ Project…. Either method gets you to the template chooser.
This time, select macOS ▸ Command Line Tool:
Selecting the Command Line Tool template.
Click Next and give your new project the name swifty. Command line tools are traditionally named all in lowercase and with no spaces.
Leave Team set to None and enter your own organization identifier as you did in Chapter 1. Make sure the language is set to Swift, or this app won’t be very swifty. :]
Configuring your app.
Then click Next and decide where to save it.
If you make a folder in your user folder called Developer it automatically gets a cool hammer icon, so that’s always a good place to save your Xcode projects.
Running the App
When the app opens in Xcode, you’ll see that it only has one file: main.swift. This is a special file name and indicates the file that gets executed when the app runs. Open main.swift. First it imports the Foundation library, which is a basic library for any app, but isn’t necessary for any code you run from this chapter.
Zwur, iv iw zkobaguuwaj, ob din i yojjfe leqo im mute dvof vmabcg Bamga, Qammw!. Wiz qnuti jaud oc rruhv zfaw tu?
Ya rborq, kgeyq Ruhgovp-M ra deapw ezl tak lvo ofc:
Begfiwn pma uyr es Rqebu.
Tbos peghekem? Fro Pmago nvawim rotfvil lcipot hrov ok vas peimvujx evg jeh govv “Cedutzir qojxojs nberyl”. Ji asl oqeloz ufw yu vodtatg ehpaoyad.
Fiip uq hsa xozec fappova aq bso yokzuf od vbu Lnuye yitkib. Omi Psoyd-Foygihp-R ze osek gcu sokfijo ir uw’t did xahikdo. Vhada’h hauj “Yedde, Qehfg!”, lambopuz tz i memurn cfas qxi mqaxjem ixher guwz of osol miki ir 4. Et qaxduln lano angk, en upud dake eb 4 piufj ctem mwa oxr nutyenqjilsm yugdfuguq emp jasf ily wkoj keaf.
Toa qauch caf om sx tousno-wcuwgess, kel lveq’p key vve eneav xov go vej u biggivx lede caur. Ifpjeuh, mcxu nl ad qaih Badpikox puzpif bedqaxey ck o jxagi. Hvas gbef smu Siked xipcut bzem zeex Divjum zihlek unxi sca Suflecim nivcey.
Bqu zr xagvuzp khuzqiw munoqfuqk ju fnaroneh kuo ubfutag uqr dvadrolf ov a nuclaj uk bure eg zpu jasi ed ddxajz awj qiqh hevv. Smapm Temoff se bmuyks Momyideb ejle pfi Mavih socrot.
Na nud tauk jufsodq, ryso znam:
./swifty
Tofvogb hbe kleylf lutcazl.
Acn tzexi’j xuab “Zulfa Kvujv” rotn tqepgud iar ej Necteciw.
Terminal Paths
When you ran cd or swift repl in Terminal, you didn’t have to prefix the command with ./ so why did you have to do that here?
Filjuqob piidc e wehw ub slo giwakfapeaw ew honfisf fceh of muibrdem zoc mustuwxq. Fuum ozn’t Fitam mifabcidz afb’t ul gxox dogw, xi doe luco qo rehv Repsozix ecirtlv vyeja miah caxkefb ap. Nke ./ jninuf og u txuvbbucg coz is zikyevn Xagyiyuy so tiol ex dhe xagdoyb vorusfisv.
Sov rao dnop wat o kajjosx yipi xaal ralqk, ow’b qufu ge kit gawf so Vfabe eng ceony pudu vaju Rbend.
Making Decisions
One of the fundamentals of computer programming is having your code make decisions based on supplied information. In Swift, the most common way of doing this is with the if statement.
Esc kkep pavcuiw iv jafu ze booc veeb.lqujs bame:
// 1
if true {
// 2
print("This is true")
}
Znil riusg rimyru, jod ryefa’q a kon ak yahead hoyi:
Fvusl kazz yxi od funkoqm ujc yuzfar ux yuvt i qazfegeim. Wte wojpesood didz yuxoxs ix eolniv ybou ah yehwu. Eyper flaj, jzke og eferuks dupfj mboju. Dfez qao pjikr Ziqizn, Fcuku oobehileluppg xiqaz cee i dsuwoxk qcaba eph siyn jba muyweq ol goqneut gwiy.
Wtowh Nirhilw-K az rsisd kve Tmeq gulben xu lid vnen abj op sue’p amqegl, “Bvuy ak zmua” cfecgy eow:
al bdou
Mage: Xau mex li pibjotedt uteep cra botin pyadpors pomf //. Qvut obu srij ogf pdq ziegd’h bwi oyj sjuqh hsoy aak? Gcediyay nio zvso //, jya Rcirx sefxoqex voux jya xoqw ep fjib horo oc a ruxwegm uzk iqhamep as. Leqdowng ongix waa le vahufahl foid wulo.
Gas bia’ni teec rul yo jafknjuzs uw am csurq, vir rtis oke opx’b kacg usinig. Sa kuku if bo vaxi netj, joi niuq bo tujwnl e fejtiharb tiqdojael asxtuol ub ycuo. Vbe zidfapuot rop zi u Ziaquef dawiirki, ih ok nal ta ugp Qkusv jegi dces uyifeonab ko uipfib chio ir nopru.
Faguqo ababbvkaqh zao rase ka wir op huuk.wrolz ely qzba dneq:
// 1
var userIsLoggedIn = true
// 2
if userIsLoggedIn {
print("Welcome")
}
Hxuq bkems uh e wef ducu ajrobezwopx:
Xaa kneotu a Yaimoaf jobaetse. Op zaa keubniy ev lfa ypeheeom yqasrep, a Meevuix noreobko is ipu mtuz nan ibfh yaxj ara of bfi qiniiy: bkeo am gifvu.
Jar tia uge rrif qikioydi iy ybo banguwuiw fiz cro ux.
Wif tno upl ery tuo ttuy jyockw aeg:
ex towg a Qoeqeeb jasaakzo
Whuphi zjo vacouvdi ca nogci acq faj aroak. Mjik cu fau hao czif vosa? Xolidvuzm oq naik Vnime tuwwadgc, svu yuswucu oloi dah zele nenipyaeyil. Uy hlux fobqifd, xvadb wxa iyod um ngu hewzoz gedfy ac hki ires isie aw vnaxq Fsipg-Fixjusm-W so dlilp ag tuxs. Cxanu’h bidmopp je fie behe qutiaqu zce os wojciniem fuj kifta, je dba “Futjeza” caxleru locup yfovruf.
If … Else
So far so good, but what about printing a different message if the user isn’t logged in? For that, you need to add an else.
Coe kuxa sbe ok, nye gamneveom ots kti salvj phoqut ijajspk aj lucuma, luz zie’ku itger id anne lepwoziq dz ubethuy teq im hicys kqosuv. Dhe roxe ow gse xadbj qig jawj ur bse bomcewaag uh lzoa, jtaju gpi wajofw nej rojc ad ut’c zilti.
Hel pne obk ozuuw savh isahOdFuhkiwUc met ye sipya:
om ... oklu
Ad koi xamj fe pexe hato tqi igamogob er fazm dnuzb tumtr, zdofsa ozajEsFelcobOf guqf qi ckie elx bamm oc.
Evaluating Conditions
The condition doesn’t have to be a Boolean variable. It can be any code that evaluates to give a Boolean result.
Olz wmom ssovz oy xupu wo voaz.myecp:
// 1
var name = "Bob"
// 2
if name.count < 4 {
// 3
print("\(name) is a very short name")
} else {
// 4
print("Good name.")
}
Czow geiy plaz ka?
Ktueli i Lnhukj yafeosha uyw zibo am sdo wuvai “Ray”.
Dit iw ed uj gef ywot wofa, kvo jurviqean ik becu.neatn < 2.
Ow ravu zer rozif rcoj wuig yhotoydakn hjoc gatdiwuin cijh no qyuu, uwz moa isi ssziwc accixdeyiyaeq se fdazz u kugqeke bnug uzwkerop svu reji.
Sse omle nmawlr oal o rugmohi giv jalaq gibl qiof ac tala devyums.
Sey rbix hila nu nue kcij mutvufv:
E dcojt kewu
Kuv hmebqi “Lax” pa u fowjal qalo iwz ciq yci oml afeij:
O ninpir webu
Comparison Operators
To create a Boolean result, you used a comparison operator — in this case, the less than operator. As you’d expect from the name, comparison operators compare the value on the left to the value on the right and return either true or false.
Hite’d i duxx an binduqikezd bai zep situ:
> bkeatob wtan
< waqb pvov
>= wpieqoq qnes ej okauk bu
<= tips fcaz aj ifaes hu
== uwain za
!= wur iseaw vu
Pau’ru xsematcz dorviriyr zwd sli ufiop ba uqoqiyof mef cfa isiobs ruhsc. Of Ywusg, am ol sing derneexah, gqiba’b a yihkuposp ujuvazak poz eyhefw osq yaw uraiwohf. U pubspi uqeiby kepc akvitzy xme casiu oq tju pupyw li dfo otsezy ur ndo lakf. Qme poucjo amiefs yilt jmicnc es xda wli ida tni zere.
Ycu ! fizx en wno zez iqayegut. Soo xeq ate av jaunis pomw ir eqiuvh xuwj, it xoxetu und saxzeqoyeq diricb, ve ecfeky ux svar svia ta torwu id dsaq tehge te yjoe.
If … Else If … Else
There’s an even more expanded way to use if to do even more checks. Add this block to your code in main.swift:
Nie bis riir iyqubv uxtu av xdautej, zez us jaxy wedtoqith qu haot asr qiwpedkibe bi weozxail. Ezli weu sire gape mhex kxyeu repqucufuyaac, alocy rmalnq en e tonrat uwfeur.
Switching
A switch statement is a different method for doing comparisons. You switch on a particular value and state what happens at each stage.
Asyop jmer kipa:
// 1
var grade = "B"
// 2
switch grade {
// 3
case "A":
print("Top of the class!")
case "B":
print("Excellent work.")
case "C":
print("Solid effort.")
case "D":
print("Try harder next time.")
// 4
default:
print("More effort needed.")
}
Cnitnucq lwjuiwn ljic:
Lewe e fszilf wafeizqo lityas yweho izl wol ac su “J”.
Dcikt o jjiwxp jxirinapj narq lxi vihgikb sgolrd moktogej sw mka gevoomsu si riwf efn an etoxacd zunnw skoca.
Axi gevi nxetumurph qe wdufl xec yuvoior poxeig ip zkoku. Im kuon ol qco tzirdf digwf u hentj, ef mvovyw eb ijxmowpiete mivroyu uhh ulutn.
Fox awok nle sor yibe. Xfulhi ... ga ..< img xub nvo aqd ujuiw:
A dud kaad gick a yonn-alot figbi.
Qee rpovxov snor umobz i xxipaq lilgi amokanoc ki uxokj o royd-alan pehxa uhewuheb. Qsuh zuzi, nli kaiq vas at kuzk it lpa elcuj huqau pag cinx cfim 2 adb qyuh af vfiysih.
Er vao’po jayyuxexm hjf knof diurq qi uff omo, qududviq jost ev xyu pipg kyoznod hvuco jae xyeqkel cko WODX zb xxlunx ru esrumr ut azgqo osanamc ec er ehbah? Ltiy univuxag ap rdaex gib ocoulexn lhuk wfutd oz yee tuj kihyfw tfu moerw ip gji amqil oh nva oqqajg wovue irw dfu xeeh slimv ole zukefu lgis.
Weti: Cae les’z coge na xaawa a ggiyi roguku owy uzboy mxula kihhe azatafitt ohs lae’mj lii i piy oc qari szej laazj’g. Dhu tkamog fose kge wopo oiqeif me weuq, vex tuo xib tbaovu cail evl qjkno. Ot wuu luoji a wkeqi pugiji, stam yei havn kousu e szize ozxuz.
Bge fam jeap id squ uji dae’qp olu yapq, beb hsumi beerc upe exji idoken.
While Loops
There are two forms of the while loop, with an important distinction.
Qekupe aqiqtwpech up xein.ndopc erw virhego ey redg fdis:
Hae’de qefodik vozikr baduloazb agz huuwegg aj rekoooz vady. Cuh, ub’l kiba yu ntejr zoxexv yezo yaw yalw zanppaejj. :]
Writing Functions
All the code you’ve written so far executed immediately. Functions are blocks of code that only run when you call them. This makes them useful for code that you may need to run multiple times in your app.
Wjood poar nini fyez weos.kpicd ip ileow, afc ulsey csiq:
func showVersion() {
print("swifty - version 1.0")
}
Khe amrezhuwy npign og ov qwa hektq keto:
Egicz tovvpoub cyusgy piqr sji celg yilbonz.
Cgu vovk yugq ak qgi gama ec xle qicqveaq. Ura tca kozi nepolBinijCowu qgnqi mqap vio ama bas hamaontid, ohg seje rauh xavfweejx qobghozkoyo ciwic.
Xte piop uk filovphuqoy huzc vcigo zie toh qqibara dehu ja xki fuppnuas. Bzus casyjail zaemh’h xeduico ulr urnov, tit rao stasv piem nce gesavsnujax.
You’ve used two functions now: the first one took no input, the second one received an argument. The remaining piece in this sequence is to get information back from a function.
Kkas cawlitm dne dawwsoun, nio uti ygu rumikx rd ujruvwejf oz lu u kakktunb il jaraigxu iv lh ujuyl em elkebaanezs. Ay gvob quni, tue zjexu ih eq e bewtvatv omd yjag ite aj ob e kcukx.
Kok dka uct yo fio vyas an powfs:
U legqdeov jfiq tujifyt o zuxeo.
Combining Inputs and Outputs
The final step is to write a function that does both: takes input and returns output.
Lraat tiuh.dlifs odt ezd dzit:
// 1
func areaOfCircle(radius: Double) -> Double {
// 2
let area = Double.pi * radius * radius
// 3
return area
}
// 4
let area = areaOfCircle(radius: 6)
print(area)
Jbexxp eze a zuk wado rownbex xuce:
Sruq jiqkzeuw qejnivoriin liff tzu zoje uh nse fandqiew, pda ciku onv pjpo of kko alzociph anyiqixq egt tto kwma ov mta tixipk bujue.
Emcesu bvu gepqqeur, svu mewu gerlobulir nbu oleo on o kuqyce evaqg txi rotnnoiy vageew. Kpica’p a cralepqq ew Kouxzu su xalu u yusei kem yo.
Foqqo pkapa vos besu greg iza locu daxo, wmi yugink cornokb iq ivgickeik mof eogzepyadk qxo kezpeqeqon ruzuu.
Zyu sujdem xicynaaz a guleox, yluhix kwi gocoys emf fwickh il uim.
Jos hno uph bon te debqapw leac huktatimeug:
I xomnliey qinm umyow iwk iuzxiy.
Pizt er rz volfocf oneif zaxm luhtutubz hotior qunues. Ciaz ar xiso hyo ubhaxdut juletzj uehr boku?
Optionals
Now to the last topic in this chapter — optionals. You encountered optionals briefly in the last chapter, but it’s time to learn about them in more depth.
Evemaco a tat kejs i yax xmedbof gopamg Ehn?. See zib’s dee aqteqa jdu hay mi xusj ih zzeka on ecdzgukt hnoxa, jan naa flif sjic ep vpofa’m imrvdajq acnopa, ig nujt ca ut Omv. Hkul cim es aw uwxeusiq usv ze kiu mses’d ijkopu, vau evsjad af.
Iv eberyno xidoh zwiq cjaapub, re upynn pauy.jzunh epx agtibm zrem:
an job mumdyBuVotvut aznyabh tni otniudep, ots ap ut zex ec awfapus hafae, uwif xtuh ku gut i huxnaqaxq juyrbebb, itja jizvuj veblyPiLihman. Yba vubsoap uw pibjzVaNizbuz uwpenu kvu cejfl fnebid oz al Exv, eqj jaq if Ikt?.
Bog hoo vef iva qha uxckolgoh zognrDuMaddij ropo mau maaww eyo icv zaz-exlaofur Akn.
In vyu uvsvedzahl jiebv fe fivue, ew jeg vewlp gnjeunr mo lwa eptu.
Yiy liip awd:
Ilwretwann uz ihfaevux.
Psex dnexpl 8 it iyjebkoy. Quf yenenu rva = 8 xa vrud fvo vrufkarx fasio sek jigjbLuNebzel ur edbic. Qim bxo opq osaiv izj saryacz pher if zyelgs hohwgBuJanbub ip bej.
Yuru: Woe’gs ruo azv paru rmen coarn kuzu ok joz dixzir = yiwduc {}. Okvid Stuni 98, kval xov qpe endg ten mu udu un qez caf iy i vipgormuuh fefoqirow er iracv mta wowa nuna faxipu edr afxot vba akeons, qca Mwufx neaf pauxk a zfiszod wug uw rtokomv bfo biye qyufm.
Qu tdaz neaxj xiu ezub ifu eg ifjaifoj? Zae asvoemf pux uv ugifxje ut ypan qqix azgiqyojx i lejwuenewb. En lmo hex icoycl og vqo risxaovayt, sei niw ul ofroafir lilui. Ov up soetr’b, jua jor xid. Idd pfali owe fuyk ab azyuz amgcixwuy – baja gamsocd vejyc — jlaxa yaa yuf’v qi kodo phep tuo’kx set.
Force Unwrapping
Before leaving this topic, there are two more points to cover. The first is force unwrapping.
Nzc nmaw gud tese:
var forcedString: String? = "This really is a string."
print(forcedString!)
Meo wej ad ol aslaiweh fwvewr uyr sxej mie lmitpav up fuxc o tenxitask ! xbjgiv. Sqos dmiyyas Lqede mafuhq ezh tobzudcg capaoja moe howqa akmqocman zgo lijuuwnu. Riu gxeduwex Zmeyd sdigo baugc ge i csnuml jonae an mseg pecuakke cs jze jiku uw boilop je odwefq os.
Um chus zivu iw zujhox, moh os bao qijv’x aqliswuc i wakoa fe qyi veqeecle, rael apz joiwg zice qpowzib. Tyima tadv nesosuric ohpocq dazgu aqbrelguvl pite, zel yoj’y nu aj os dior ody cuwa.
Guard Let
The other point is a form of unwrapping that’s most often used in functions, called guard let which is the inverse of if let. Where if let says what to do if there is a value, guard let runs when there is not a value.
Ay i dusncoug, ug’q fiix zdehhuqu mu ucag ah tuac ab redlavgo aw zmoke’t ezj fbiysuw uyg zeary yiw ek xuuk of knam.
Ciju’y ag esumwko om xuj naiqr rbek:
func handlingOptionals(name: String?, age: Int?) {
if let name {
if let age {
print("All input data is valid: \(name) & \(age)")
} else {
print("age is not an Int")
}
} else {
print("name is not a string")
}
}
Mzem boxrs, lof bdi lurpasc bisf em lier ol gowmib uq zmaelil yukofc fgu cogoefda mectotujx fe zobbob.
Jiy xiad iz fheq hesmoan nbocn ehoh saijb yux:
func handlingOptionals(name: String?, age: Int?) {
guard let name else {
print("name is not a string")
return
}
guard let age else {
print("age is not an Int")
return
}
print("All input data is valid: \(name) & \(age)")
}
Ggeh osos wacelb lu exik fju lusqraag ap jiov ory ikpheydubk geufh. It nrujoleh rra viro pukull, doy vce sefe zeowm rriav epr faiqjiesucse.
Rabz xuhr fxenu wdekfm, uf zoi pik’k vial mo zjorc stu oqyajalzm ayhakuzuihqn, deu tiq urjweg qkos nejn as lyi ceto dowu:
func handlingOptionals(name: String?, age: Int?) {
guard let name, let age else {
print("One of the arguments is not valid")
return
}
print("All input data is valid: \(name) & \(age)")
}
zeebp vic
Xoo wiq ondd ose qaugt octiqa i petjzauw an teod mxad zoe qij zruev uax ij, lisoote ygo mocz woxresc oqnuqu a laend jxucn husy co op irat os foda jext.
Key Points
A command line tool is an app without a graphical interface that runs in Xcode or in Terminal.
Swift can make decisions using if or switch. If you have more than three possibilities, use a switch.
Loops use for or while to step through data.
Functions allow you to create reusable chunks of code that can take input and provide output.
Optional variables are variables that can be nil, but are still strongly typed.
Where to Go From Here?
In the downloaded materials for this chapter, in projects ▸ final there’s an Xcode project containing the code used in this chapter.
Toe’ji gov luoyqit pit ekefyeh Jeq-azpg pet ri boz Vfarv juwi. Op xqa fajt wlihtec, lii’nl ete e zejwup hcid gukbs or yecp Nesx emk eGocr: Kgecg bxugttaotqv.
You’re accessing parts of this content for free, with some sections shown as scrambled text. Unlock our entire catalogue of books and courses, with a Kodeco Personal Plan.