Go (програмски језик) — разлика између измена

Садржај обрисан Садржај додат
(by SublimeText.Mediawiker)
Нема описа измене
Ред 8:
|модел = [[Императивно програмирање|императивни]], [[Конкурентно програмирање|конкурентни]]
|настанак =
|аутори = -{[[Google Inc.]]}-, доприносиоци из заједнице [[отворени код|отвореног кода]]
|дизајнери = Роберт Грисемер, <br>Роб Пајк, <br>[[Кен Томпсон]]
|актуелна верзија = 1.6
|датум актуелне верзије = 17 фебруар 2016
|типови =
|имплементације = -{gc}- (главна имплементација), -{gccgo}- (у оквиру [[ГНУ]] колекције компајлеракомпилатора), -{gopherjs}- (компајлијрапреводи Гоу програме у [[JavaScript]])
|дијалекти =
|утицаји = [[Alef (програмски језик)|Alef]], [[APL (програмски језик)|APL]], [[C (програмски језик)|C]], [[Комуницирајући секвенцијални процеси|CSP]], [[Limbo (програмски језик)|Limbo]], [[Modula-2]], [[Newsqueak]], [[Oberon]], [[Паскал|Паскал (програмски језик)]], [[Пајтон (програмски језик)|Пајтон]], [[Smalltalk]]
Ред 33:
Језик је настао као експеримент тројице Гуглових запослених—Роберт Грисемер, Роб Пајк и Кен Томпсон. Идеја је била да се дизајнира нови језик за системско програмирање који би решио главне проблеме постојећих језика у тој групи а притом задржао њихове позитивне особине. Нови језик би имао следеће особине:
 
* био би [[статичка компилација|статички компајлиранкомпилиран]] и могао би да се се користи за велике системе (као [[Java]] и [[C++]]),
* програмирање би било продуктивно а програми читљиви, без превише обавезних кључних речи и понављања (као код [[динамички програмски језик|динамичких језика]]),
* не би захтевао компликоване алате, већ би их добро подржао
Ред 78:
Гоу такође додаје синтаксу за иницијализацију параметара у <code>struct</code> типу по имену, као и за иницијализацију мапа и низова.
 
Као замену за C-ове <code>for</code>, <code>while</code> и <code>do</code>/<code>while</code> петље, Гоу уводи комбиновану <code>for</code> петљу која заједно са <code>range</code> изразом омогућује једноставну итерацију око низова, одсечака, мапа, канала, и стрингованиски.
 
=== Типови података ===
 
Гоу има одређен број уграђених типова података, укључујући [[Булов тип података]], нумеричке типове ({{mono|<code>byte}}</code>, {{mono|<code>rune}}</code>, {{mono|<code>int}}</code>, {{mono|<code>float}}</code>, {{mono|<code>complex}}</code>), и [[ниска|ниске]]. Ниске су непроменљиве, а помоћу уграђених оператора и кључних речи могуће је спајање, поређење и кодирање из и у [[UTF-8]]. Сложени типови ({{јез-енг|record type}}) се могу дефинисати уз помоћ кључне речи {{mono|<code>struct}}</code>.
 
Типом податка {{mono|<code>T}}</code> и бројем елемената {{mono|<code>n}}</code> се дефинише '''[[Низ (структура података)|низ]]''' означен са {{mono|<code>[n]T}}</code>; пошто је број елемената део типа податка, низови којима су типови елемената исти али им је број елемената различит, су различитог типа.
 
[[Динамички низ]]ови се зову '''одсечци''' {{јез-енг|slice}}; за тип податка {{mono|<code>T}}</code>, одсечак се означава са {{mono|<code>[]T}}</code>. Ови низови имају дужину и капацитет којим се означава када треба заузети нови део меморије за проширење одсечка. Неколико одсечака може да дели одређени меморијски простор.
 
За пар типова података {{mono|<code>K, V}}</code>, тип {{mono|<code>map[K]V}}</code> означава тип '''мапе''' ([[хеш табела]]) која мапира кључеве типа {{mono|<code>K}}</code> на вредности типа {{mono|<code>V}}</code>. Хеш табеле су уграђене у језик, имају посебну синтаксу, и над њима се операције врше уграђеним функцијама.
 
'''Канали''' ({{јез-енг|channel}}) за комуникацију између конкурентских процеса такође имају своју синтаксу. За тип податка {{mono|<code>T}}</code>, тип канала се означава са {{mono|<code>chan T}}</code>. Језик поседује и скуп уграђених операција којима се вредности могу примати и слати преко канала.
 
'''[[Показивач (програмирање)|Показивачи]]''' постоје за све типове података; за тип податка {{mono|<code>T}}</code>, показивач се означава са {{mono|<code>*T}}</code>. За разлику од C-а, нема показивачке аритметике, осим кроз тип {{mono|<code>Pointer}}</code> из пакета {{mono|<code>unsafe}}</code> у стандардној библиотеци.
 
Поред подршке за интерфејсе, систем типова је '''номиналан''' (тј. заснива се на експлицитном именовању типова података). Кључна реч {{mono|<code>type}}</code> ствара нови тип податка, који се разликује од осталих типова података који могу имати исти распоред у меморији (а у случају {{mono|<code>struct}}</code> типа, и исти редослед поља). Неке конверзије између типова су уграђене, а додавање новог типа се могу дефинисати додатне конверзије. Конверзије између типова су увек експлицитне.
 
На пример, помоћу кључне речи {{mono|<code>type}}</code> се може дефинисати тип за [[IP адреса|IPv4]] адресе, које су 32-битни цели бројеви без предзнака:
 
<syntaxhighlight lang="go">
Ред 102:
</syntaxhighlight>
 
Са овом дефиницијом типа {{mono|<code>ipv4addr(x)}}</code> интерпретира {{mono|<code>uint32}}</code> вредност у ИП адресу. Просто додељивање вредности {{mono|<code>x}}</code> променљивој чији је тип {{mono|<code>ipv4addr}}</code> није могуће јер, иако имају исту структуру у меморији, нису исти типови.
 
Константни изрази могу имати или немати типове; ако немају тип податка, он им се додељује када се њихова вредност додели некој променљивој, под условом да је конверзија могућа током компилације.
 
'''Функције''' такође имају типове. Могу да прихватају ниједан или више аргумената и да врате ниједну или више вредности; све ове вредности имају своје типове, а заједно они одређују потпис, односно тип функције. На пример, {{mono|<code>func(string, int32) (bool, error)}}</code> је тип функције која као аргументе прима текст и 32-битни број са предзнаком (редом, {{mono|<code>string}}</code> и {{mono|<code>int32}}</code>), а враћа [[Булов тип података|бул]] и грешку (редом, {{mono|<code>bool}}</code> и {{mono|<code>error}}</code>).
 
Сваки именовани тип може имати сет '''метода''' који је са њим повезан. Претходни пример се може проширити тако да има методе којим се врши штампање у читљивом формату, проверава да ли се налази у одређеном опсегу и слично, зависно од функционалности коју тип треба да има. Типу се метода додаје тако што се између кључне речи {{mono|<code>func}}</code> и имена функције дода прималац ({{јез-енг|receiver}}), који се састоји од имена које представља референцу (слично речима {{mono|<code>this}}</code> и {{mono|<code>self}}</code> у језицима као што су [[Јава (програмски језик)|Јава]] и [[Пајтон (програмски језик)|Пајтон]]) и типа на који се метода односи.
 
<syntaxhighlight lang="go">
Ред 117:
</syntaxhighlight>
 
Због номиналног система типова, ова метода је додата типу {{mono|<code>ipv4addr}}</code>, али не и типу {{mono|<code>uint32}}</code>.
 
Иако за њихово дефинисање и позивање постоји посебна синтакса, методе немају засебан тип. Сама синтакса је заправо "синтаксни шећер" ({{јез-енг|syntactic sugar}}), па ако је {{mono|<code>x}}</code> променљива којој је додељена вредност чији је тип горепоменути {{mono|<code>ipv4addr}}</code>, следеће две линије имају исто значење:
 
<syntaxhighlight lang="go">
Ред 132:
Протоколи омогућују ограничен облик структурних типова података у оквиру номиналног система типова података. Сваки тип података над којим су дефинисане све методе из интерфејса имплицитно задовољава тај интерфејс. Сам систем интерфејса заснован је на систему протокола из језика [[Smalltalk]]. Интерфејс групише типове података у скуп, тако што сам представља листу метода које ти типови морају садрже. Типови који задовољавају одређени интерфејс не морају експлицитно то да нагласе, већ се та провера врши током компилације програма.
 
Типови {{mono|<code>Квадрат}}</code> и {{mono|<code>Круг}}</code> се могу груписати помоћу интерфејса {{mono|<code>Облик}}</code> који од својих типова захтева да садрже методе {{mono|<code>Обим}}</code> и {{mono|<code>Површина}}</code>.
 
<syntaxhighlight lang="go">
Ред 163:
</syntaxhighlight>
 
Сада се може дефинисати функција {{mono|<code>СабериПовршине}}</code> која тражи два аргумента који задовољавају интерфејс {{mono|<code>Облик}}</code> и сабира њихове површине:
 
<syntaxhighlight lang="go">
Ред 173:
</syntaxhighlight>
 
Пошто је задовољење интерфејса имплицитно, додавање нових типова (нпр. {{mono|<code>Троугао}}</code> или {{mono|<code>Трапез}}</code>) се своди на дефинисање структуре типа и имплементације одређених метода, а то се може извршити и у оквиру другог пакета.
 
Стандардна библиотека језика користи интерфејсе у оквиру неколико библиотека. Један од примера је {{mono|<code>Stringer}}</code> интерфејс из пакета {{mono|<code>fmt}}</code>, који захтева методу <code>String() string</code>; задовољењем овог интерфејса, сваки тип може да одреди како ће његова вредност изгледати приликом штампе. Други пример су интерфејси {{mono|<code>Reader}}</code> и {{mono|<code>Writer}}</code>, којима се дефинише протокол за улаз и излаз података помоћу метода {{mono|<code>Read}}</code> и {{mono|<code>Write}}</code>, а користи код пакета за рад са [[датотека]]ма, [[мрежни сокет|мрежним сокетима]], стандардним улазом и излазом, баферима [[бајт]]ова, токовима, , и слично.
 
Празан интерфејс (<code>interface{}</code>) представља важан случај у оквиру система типова, јер се односи на било који тип податка. Сличан је типу <code>Object</code> у језицима Јава и C#; разликује се од њих по томе што је то интерфејс који задовољавају сви типови укључујући и уграђене као што је <code>int</code>, док <code>Object</code> може држати само инстанце објеката јер представља надтип ({{јез-енг|supertype}}). Податак који је сачуван под типом <code>interface{}</code> се не може користити као аргумент при позиву функција или са уграђеним операторима без конверзије у конкретан тип помоћу ''наговештавања типа'' ({{јез-енг|type assertion}}), ''гранања по типу'' ({{јез-енг|type switch}}), или испитивањем [[рефлексија (програмирање)|рефлексијом]] уз помоћ <code>reflect</code> пакета. Зато што може да држи било који тип податка, <code>interface{}</code> представља један од начина за имплементацију генеричких алгоритама.
<!-- Поред интерфејса,
 
=== Систем пакета ===
Празан интерфејс ({{mono|interface{}}}) представља важан случај у оквиру система типова. -->
 
Сваки пакет је дефинисан са два податка: својом путањом (нпр. <code>"compress/bzip2"</code> или <code>"golang.org/x/net/html"</code>) и својим именом (нпр. <code>bzip2</code> или <code>html</code>). Путања пакета је ниска, па може имати било какав садржај; пакети које корисници објављују на интернету садрже [[URL|адресу]] са које пакет може бити преузет, чиме је олакшано управљање пакетима. Позив на други пакет увек садржи и име тог пакета, а да би нека вредност из пакета била видљива, њено мора почињати великим словом (нпр. функција <code>Printf</code> из пакета <code>fmt</code> је видљива у свим другим пакетима који позивају тај пакет, док је функција <code>printf</code> видљива само у оквиру <code>fmt</code> пакета).
== Систем пакета ==
 
=== Конкурентно програмирање ===
 
=== Изостављене особине ===
 
== Правила и стил ==
 
* Форматирање програма, укључујући индентацију, размаке, положаје заграда и други детаљи визуелног дела кода су стандардизовани уз помоћ алатке <code>gofmt</code>; програм <code>golint</code> врши додатне стилске провере кода.
* Алати и пакети из стандардне библиотеке сугеришу стандардан начин приступа различитим проблеимима као што су документација (<code>godoc</code>), тестирање (<code>go test</code>), компилација програма (<code>go build</code>),управљање пакетима (<code>go get</code>) итд.
* Компајлер уводи стриктно поштовање правила која у другим језицима постоје само у облику препорука. Неки од примера укључују забрану кружних зависности (два пакета не могу зависити један од другог), забрану неискориштених пакета и променљивих, и недостатак имплицитних конверзија типова.
* Изостављање неких од особина, као што је <code>map</code> функција из функционалних језика и <code>try</code>/<code>catch</code>/<code>finally</code> структура из објектних језика захтева стил програмирања који је експлцитан, конкретан и императиван.
 
== Алати ==
 
Стандардна Гоу дистрибуција садржи следеће алате:
 
* <code>go build</code>, који компилира изворни код у извршне датотеке
* <code>go run</code>, који покреће програм без компилације, као скрипту
* <code>go test</code>, који покреће систем за тестирање и мерење перформанси програма
* <code>go fmt</code>, који форматира датотеке са изворним кодом сходно договореним правилима
* <code>go get</code>, који служи за управљање спољашњим пакетима помоћу различитих [[систем контроле верзија|система контроле верзија]]
* <code>go vet</code>, који проналази грешке помоћу [[статичка анализа програма|статичке анализе програма]]
* <code>godoc</code>, који приказује документацију пакета у [[командна линија|командној линији]] или [[веб читач]]у
* <code>gorename</code>, који служи за безбедно преименовање типова, функција и променљивих
* <code>go generate</code>, који служи за покретање генеришућих програма као што је [[Yacc]]
 
Поред ових алата, корисници су допринели пишући своје програме који допуњују овај скуп алата. Неки од примера су <code>goimports</code> који проверава које пакете програм користи или не користи, па их додаје или брише са списка, <code>gocode</code>, који у оквиру различитих [[уређивач текста|уређивача текста]] нуди информације о доступним типовима и функцијама, и <code>golint</code>, који указује на честе грешке у програмима и на недостатак документације.
 
Писање пакета је знатно олакшано постојањем <code>go</code> пакета у стандардној библиотеци, који нуди различите механизме за управљање и анализу датотека са изворним кодом.
 
== Примери ==
Линија 200 ⟶ 227:
}
</syntaxhighlight>
 
=== Конкурентан пример ===
 
== Корисници и прихватање ==