Notitie
Voor toegang tot deze pagina is autorisatie vereist. U kunt proberen u aan te melden of de directory te wijzigen.
Voor toegang tot deze pagina is autorisatie vereist. U kunt proberen de mappen te wijzigen.
(Opmerking: oudere versies van CNTK gebruikten "MEL" (Model editing Language) voor deze doeleinden. We zijn nog bezig met het converteren van de voorbeelden. Zie de hiervoor documentatie over MEL.
MET CNTK kunnen modellen na het feit worden bewerkt. Dit wordt gedaan door een nieuw model te maken tijdens het klonen (delen van) een bestaand model waarop wijzigingen zijn toegepast. Hiervoor biedt CNTK drie basisfuncties:
-
BS.Network.Load()een bestaand model laden -
BS.Network.CloneFunction()om een sectie van een bestaand model te extraheren voor hergebruik -
BS.Network.Edit()om een model te klonen met wijzigingen van knooppunten op knooppunt toegepast
De bewerking is geen afzonderlijke stap. In plaats daarvan zou een opdracht die van een gewijzigd model moet werken, geen modelPath opgeven van waaruit het model moet worden geladen, maar in plaats daarvan een BrainScriptNetworkBuilder sectie waarmee het model binnen wordt geladen en een nieuw model wordt gemaakt van het geladen model.
Voorbeeld: Discriminerende pretraining
Discriminerende pretraining is een techniek waarbij een diep netwerk wordt gemaakt door een reeks ondiepere netwerken te trainen. Begin met een netwerk met één verborgen laag, train naar gedeeltelijke convergentie, verwijder vervolgens de uitvoerlaag, voeg een nieuwe verborgen laag toe en voeg een nieuwe uitvoerlaag toe. Herhaal dit totdat het gewenste aantal verborgen lagen is bereikt.
Laten we ervan uitgaan dat we een heel eenvoudig startmodel hebben
BrainScriptNetworkBuilder = [
N = 40; M = 9000; H = 512
W1 = Parameter (H, N); b1 = Parameter (H)
Wout = Parameter (M, H); bout = Parameter (M)
x = Input (N, tag=‘feature’) ; labels = Input (M, tag=‘labels’)
h1 = Sigmoid (W1 * x + b1)
z = Wout * h1 + bout
ce = CrossEntropyWithSoftmax (labels, z, tag=‘criterion’)
]
Laten we dit model trainen en opslaan onder model.1.dnn. Vervolgens willen we een model trainen met twee verborgen lagen, waarbij de eerste verborgen laag wordt geïnitialiseerd op basis van de waarden die hierboven zijn getraind. Hiervoor maken we een afzonderlijke trainingsactie waarmee een nieuw model wordt gemaakt, maar onderdelen van de vorige opnieuw worden gebruikt, als volgt:
BrainScriptNetworkBuilder = {
# STEP 1: load 1-hidden-layer model
inModel = BS.Network.Load ("model.1.dnn")
# get its h1 variable --and also recover its dimension
h1 = inModel.h1
H = h1.dim
# also recover the number of output classes
M = inModel.z.dim
# STEP 2: create the rest of the extended network as usual
W2 = Parameter (H, H); b2 = Parameter (H)
Wout = Parameter (M, H); bout = Parameter (M)
h2 = Sigmoid (W2 * h1 + b2)
z = Wout * h2 + bout
ce = CrossEntropyWithSoftmax (labels, z, tag=‘criterion’)
}
Stap 1 gebruikt eerst Load() om het netwerk in een BrainScript-variabele te laden. Het netwerk gedraagt zich als een BrainScript-record, waarbij alle knooppunten op het hoogste niveau (alle knooppunten die geen . of [ in hun knooppuntnamen bevatten) toegankelijk zijn via recordsyntaxis. Een nieuw netwerk kan verwijzen naar elk knooppunt in een geladen netwerk. In dit voorbeeld bevat het geladen netwerk een knooppunt h1 dat de uitvoer is van de eerste verborgen laag en een knooppunt z dat de niet-genormaliseerde logboekposterale kans is van de uitvoerklassen (invoer voor de softmax-functie). Beide knooppunten kunnen worden geopend vanuit BrainScript via puntsyntaxis, bijvoorbeeld inModel.h1 en inModel.z.
Houd er rekening mee dat constanten niet worden opgeslagen in modellen, dus N en M zijn niet beschikbaar in het model. Het is echter mogelijk om ze te reconstrueren van het geladen model. Voor dat doel gedragen rekenknooppunten zich ook als BrainScript-records en stellen ze een dim eigenschap beschikbaar.
Vervolgens bouwt STAP 2 de rest van het nieuwe netwerk met behulp van reguliere BrainScript. Houd er rekening mee dat in deze nieuwe sectie eenvoudigweg het knooppunt wordt gebruikt h1 van het invoermodel als invoer, zoals bij elk ander knooppunt. Als u verwijst naar een knooppunt van het invoernetwerk, worden automatisch alle knooppunten waarvan dit knooppunt afhankelijk is, ook onderdeel van het zojuist gemaakte netwerk. Het invoerknooppunt x maakt bijvoorbeeld automatisch deel uit van het nieuwe netwerk.
Houd er ook rekening mee dat de uitvoerlaag opnieuw is samengesteld. Op deze manier worden de modelparameters nieuw gemaakt. (Om dat niet te doen en in plaats daarvan de bestaande parameters opnieuw te gebruiken, kunt u inModel.Woutgebruiken, maar houd er rekening mee dat dit niet logisch is vanuit het oogpunt van het netwerkontwerp in dit specifieke voorbeeld.)
Voorbeeld: Een vooraf getraind model gebruiken
Hier volgt een voorbeeld van het gebruik van een vooraf getraind model (van bestand "./featext.dnn") als functie-extractor:
BrainScriptNetworkBuilder = {
# STEP 1: load existing model
featExtNetwork = BS.Network.Load ("./featext.dnn")
# STEP 2: extract a read-only section that is the feature extractor function
featExt = BS.Network.CloneFunction (
featExtNetwork.input, # input node that AE model read data from
featExtNetwork.feat, # output node in AE model that holds the desired features
parameters="constant") # says to freeze that part of the network
# STEP 3: define the part of your network that uses the feature extractor
# from the loaded model, which above we isolated into featExt().
# featExt() can be used like any old BrainScript function.
input = Input (...)
features = featExt (input) # this will instantiate a clone of the above network
# STEP 4: and add the remaining bits of the network in BrainScript, e.g.
h = Sigmoid (W_hid * features + b_hid) # whatever your hidden layer looks like
z = W_out * h + b_out
ce = CrossEntropyWithSoftmax (labels, z)
criterionNodes = (ce)
}
STAP 1 maakt gebruik van Load() om het netwerk in een BrainScript-variabele te laden.
STAP 2 maakt gebruik van CloneFunction() om de sectie met betrekking tot functieextractie te klonen vanuit het geladen netwerk. Dit is de subgrafiek die featExtNetwork.input verbindt met featExtNetwork.feat. Omdat we parameters="constant"hebben opgegeven, worden alle parameters die featExtNetwork.feat afhankelijk zijn ook gekloond en alleen-lezen gemaakt.
In STAP 3 en 4 wordt het nieuwe netwerk gedefinieerd. Dit gebeurt net als elk ander BrainScript-model, alleen dat we nu de featExt() functie hiervoor kunnen gebruiken.
Problemen met knooppuntnamen met .[ en ]
Als u wilt verwijzen naar een knooppunt in een netwerk dat . of [ of ]bevat, vervangt u deze tekens door _.
Als network bijvoorbeeld een knooppunt met de naam result.zbevat, mislukt network.result.z; zeg in plaats daarvan network.result_z.
Voorbeeld: Knooppunten van een bestaand netwerk wijzigen
Als u binnenste delen van een bestaand netwerk wilt wijzigen, zou het netwerk daadwerkelijk worden gekloond, terwijl wijzigingen worden toegepast als onderdeel van het kloonproces. Dit wordt bereikt door BS.Network.Edit().
Edit() wordt herhaald over alle knooppunten van een netwerk en biedt elk knooppunt, één voor één, aan lambda-functies die door de aanroeper worden doorgegeven. Deze lambda-functies kunnen vervolgens het knooppunt inspecteren en het knooppunt ongewijzigd retourneren of een nieuw knooppunt op zijn plaats retourneren.
Edit() wordt herhaald over knooppunten in niet-opgegeven volgorde. Als een vervangend knooppunt verwijst naar een netwerkknooppunt dat op zijn beurt is vervangen, werkt Edit() als laatste stap alle verwijzingen naar de respectieve vervangingen bij (ook wel 'doe het juiste').
Takenlijst: voorbeeld.
Volgende: volledige functiereferentie