2014-06-20 12 views
10

Starałem się zrozumieć, jak działają pakiety lepiej pod względem tego, co faktycznie egzekwuje golang, a nie tego, co zwykle robi się lub jest uważane za dobrą praktykę (o dobrej praktyce możemy mówić później, ale życzę zrozumieć najpierw).Jak działają pakiety w golang

Od effective go mówi:

„Inna konwencja jest taka, że ​​nazwa pakietu to nazwa podstawa jego katalogu źródłowego ...”

Jednak powyższy opis nie wydaje być zmuszonym przez pójście lub wymagane. Tak więc zastanawiałem się, czy mogłem mieć wiele różnych plików z różnych deklaracji pakietu na szczycie w tej samej bazie katalogowej. Jeśli mogę mieć wiele deklaracji pakietu w tym samym katalogu, w jaki sposób mogę je następnie zaimportować i użyć każdego z osobna w tym samym pliku? Zasadniczo, myślę, że jeden z problemów, który mam, wynika ze sformułowania części samouczka/dokumentacji. Jeśli jest to zgodnie z konwencją, to dla mnie oznacza to, że jest to NIE wymuszane przez język. Ponieważ na przykład, programiści NIE piszą słowa kluczowego func dla funkcji według konwencji. Piszemy func, ponieważ w przeciwnym razie wykrzyczymy na ciebie i to nie będzie kompilować. Dlatego chciałbym to wyjaśnić za pomocą przykładu poniżej (i jeśli to możliwe, zmienić dokumentację na czas, ponieważ moim zdaniem jest to wielka sprawa, jak można to zrobić?).

Na przykład, że mam trzy plik A.go, B.go, C.go że wydrukowania funkcji drukowania Print() że po prostu drukuje A, B, C odpowiednio. Wszystkie znajdują się w tym samym katalogu bazowym o nazwie być może base. Następnie każdy ma inną deklarację pakietu: package Apkg, package Bpkg, package Cpkg.

jak byś potem je zrobił i zaimportował? Czy coś takiego jak praca będzie działać?

package main 

import(
    nameA "github.com/user_me/base/Apkg" 
    nameB "github.com/user_me/base/Bpkg" 
    nameC "github.com/user_me/base/Cpkg" 
) 

func main() { 
    nameA.Print() \\prints a 
    nameB.Print() \\prints b 
    nameC.Print() \\prints c 
} 

a może nawet nie trzeba podać nazwę jeśli statments pakietowe to szczyt to już inna:

package main 

import(
    "github.com/user_me/base" 
) 

func main() { 
    Apkg.Print() \\prints a 
    Bpkg.Print() \\prints b 
    Cpkg.Print() \\prints c 
} 

plik druku to:

A.go:

//file at github.com.user_me/base and name A.go 
package Apkg 

import "fmt" 

func Print(){ 
    fmt.Println("A") 
} 

B.go:

//file at github.com.user_me/base and name B.go 
package Bpkg 

import "fmt" 

func Print(){ 
    fmt.Println("B") 
} 

C.go: // plik na github.com.user_me/podstawa i nazwisko C.go pakietu Cpkg

import "fmt" 

func Print(){ 
    fmt.Println("C") 
} 

Ponadto, jeśli można mieć nazwę inny z base , czy ktoś mógłby mi wyjaśnić, jak import jest rzeczywiście wykonywany? Jeśli nazwa pakietu to package Apkg w bazie, import musi być import github.com/user_me/base lub import github.com/user_me/base/Apkg lub github.com/user_me/Apkg.

Nie przetestowałem jeszcze tego, ale zrobię to wkrótce.Importowanie transakcji w podróży było dla mnie trochę dezorientujące i chciałbym uzyskać odpowiedź i podzielić się nią ze światem.

Odpowiedz

7

Nie, to 1 pakiet na folderze, więc trzeba by mieć je:

$GOPATH/src/github.com/user_me/base/Apkg/a.go 
$GOPATH/src/github.com/user_me/base/Bpkg/b.go 
$GOPATH/src/github.com/user_me/base/Cpkg/c.go 

Nie można nawet zbudować go inaczej:

┌─ [email protected] [/t/blah]                           
└──➜ go build 
can't load package: package .: found packages pkgA (blah1.go) and pkgB (blah2.go) in /tmp/blah 

Twoje imię i nazwisko pakiet nie muszą mieć taką samą nazwę jak katalog, w którym się znajdują, jednak wszystkie pliki w jednym katalogu muszą mieć tę samą nazwę pakietu.

Można również zmienić nazwę paczki na import, na przykład:

import (
    cr "crypto/rand" 
    mr "math/rand" 
) 

Albo biblioteka nazywa main (zły pomysł btw):

import m "github.com/user_me/base/main" 
+0

Więc to nie jest dobre "konwencja", z język wymusza to? –

+0

Tak, na przykład sprawdź aktualizację – OneOfOne

+0

Ciekawe, że wyrażają to w tak dziwny sposób, wypowiadając swoją "konwencję", jeśli język ją wymusza. Powodem, dla którego byłem sceptyczny i zdezorientowany, było to, że wcześniej miałem nazwę pakietu na górze moich plików dla "bazy", która NIE pasowała do nazwy podstawowego katalogu. Tak więc na przykład miałem 'pakiet superBase' zamiast' pakietu base' i nadal byłem w stanie uruchomić 'go test' mimo że mój import był' import baseName github.com/user_me/base', ale pakiet dla każdego pliku był "pakiet superBase". Dziwne. Czy jest to wyjątkowe w przypadku testu "idź"? –