📄 hparse.c
字号:
FreeLinkSet(p->pred); --numNodes; Dispose(&nodeHeap,p);}/* ShrinkNode: reduces sizes of LinkSets to minimum */static void ShrinkNode(Link p){ LinkSet *ls; ls = p->succ; if (ls->maxLinks > ls->numLinks) ResizeLinkSet(ls,ls->numLinks); ls = p->pred; if (ls->maxLinks > ls->numLinks) ResizeLinkSet(ls,ls->numLinks);}/* FreeNetwork: free storage allocated for network */void FreeNetwork(HPNetwork *network){ Link p = network->chain; Link q; while (p!=NULL) { q = p->chain; FreeNode(p); p = q; }}/* NotLinked: returns true if node x is not in link set ls */static Boolean NotLinked(LinkSet *ls, Link x){ int i; Link *p; p = ls->links+1; for (i=1; i<=ls->numLinks;i++,p++) if (x == *p) return FALSE; return TRUE;}/* JoinNodes: join node a -> node b */void JoinNodes(Link a, Link b){ LinkSet *asucc,*bpred; asucc = a->succ; bpred = b->pred; if (NotLinked(asucc,b)) { if (asucc->numLinks == asucc->maxLinks) { ResizeLinkSet(asucc,(int)(asucc->maxLinks*LINKEXTENTFACTOR+1)); } asucc->links[++(asucc->numLinks)] = b; if (asucc->nUse<0) asucc->nUse = -(asucc->nUse); /* undo marks */ } if (NotLinked(bpred,a)) { if (bpred->numLinks == bpred->maxLinks) { ResizeLinkSet(bpred,(int)(bpred->maxLinks*LINKEXTENTFACTOR+1)); } bpred->links[++(bpred->numLinks)] = a; if (bpred->nUse<0) bpred->nUse = -(bpred->nUse); /* undo marks */ }}/* TailMerge: join a to b by sharing succ link sets */void TailMerge(Link a, Link b){ Link pNode; LinkSet *shared,*bpred; bpred = b->pred; pNode = bpred->links[1]; /* assume all preds share same link set */ shared = pNode->succ; ++(shared->nUse); FreeLinkSet(a->succ); a->succ = shared; if (NotLinked(bpred,a)) { if (bpred->numLinks == bpred->maxLinks) { ResizeLinkSet(bpred,(int)(bpred->maxLinks*LINKEXTENTFACTOR+1)); } bpred->links[++(bpred->numLinks)] = a; }}/* HeadMerge: join a to b by sharing pred link sets */void HeadMerge(Link a, Link b){ Link sNode; LinkSet *shared,*asucc; asucc = a->succ; sNode = asucc->links[1]; /* assume all succs share same link set */ shared = sNode->pred; ++(shared->nUse); FreeLinkSet(b->pred); b->pred = shared; if (NotLinked(asucc,b)) { if (asucc->numLinks == asucc->maxLinks) { ResizeLinkSet(asucc,(int)(asucc->maxLinks*LINKEXTENTFACTOR+1)); } asucc->links[++(asucc->numLinks)] = b; }}/* PrintNode: print node p to stdout */static void PrintNode(Link p){ PrModelName(p); printf("%s\n",(p->extName==NULL)?"<Blank>":p->extName->name); printf(" Pred: "); PrintLinkSet(20,p->pred); printf(" Succ: "); PrintLinkSet(20,p->succ); fflush(stdout);}/* PrintHParseNetwork: print network to stdout */static void PrintHParseNetwork(HPNetwork *network){ Link p = network->chain; while (p!=NULL) { PrintNode(p); p=p->chain; } printf("\n");} /* PrintStats: print stats on memory usage */void PrintStats(void){ printf("Network Memory Usage:\n"); printf("Nodes: %ld Nodes, %ld Bytes\n",numNodes,numNodes*sizeof(Node)); printf("Links: %ld Sets, %ld Slots, %ld Bytes\n",numLinkSets, numLinks, numLinks*sizeof(Link)+numLinkSets*sizeof(LinkSet)); fflush(stdout);}/* --------------------------- Network Handling ---------------------- */static Link curChain; /* current network being built *//* CloneNetwork: returns a clone of given network. Works by attaching a copy of each node in prototype to user slot, then replacing each link to node p in the copies by a link to p->user */HPNetwork CloneNetwork(HPNetwork prototype){ HPNetwork clone; Link p = prototype.chain; Link *oldL,*newL,q,p2,q2; int i,nx,nu; clone.chain=NULL; while (p!=NULL) { /* copy all nodes of prototype */ q = CreateNode(p->modelName,&clone.chain,0,0); q->extName = p->extName; p->user = (Ptr) q; p=p->chain; } p = prototype.chain; /* now fix links */ while (p!=NULL) { q=(Link)p->user; if (q->succ == NULL && p->succ != NULL) { /* otherwise its null or */ q->succ = CreateLinkSet(p->succ->maxLinks); /* already shared */ q->succ->numLinks = p->succ->numLinks; oldL=p->succ->links+1; newL=q->succ->links+1; for (i=1; i<=p->succ->numLinks; i++) { *newL++ = (Link) (*oldL)->user; oldL++; } if ((nu=p->succ->nUse) > 1) { /* shared linkset */ p2 = prototype.chain; nx = 1; while (p2 != NULL){ if ( p != p2 && p->succ == p2->succ){ ++nx; q2 = (Link)p2->user; if (q2->succ != NULL) HError(3190,"CloneNetwork: Overwriting a succ linkset"); q2->succ = q->succ; } p2 = p2->chain; } if (nu != nx) HError(3190,"CloneNetwork: shared succ linkset count %d vs %d",nx,nu); q->succ->nUse = nu; } } if (q->pred == NULL && p->pred != NULL) { /* otherwise its null or */ q->pred = CreateLinkSet(p->pred->maxLinks); /* already shared */ q->pred->numLinks = p->pred->numLinks; oldL=p->pred->links+1; newL=q->pred->links+1; for (i=1; i<=p->pred->numLinks; i++) { *newL++ = (Link) (*oldL)->user; oldL++; } if ((nu=p->pred->nUse) > 1) { /* shared linkset */ p2 = prototype.chain; nx = 1; while (p2 != NULL){ if ( p != p2 && p->pred == p2->pred){ ++nx; q2 = (Link)p2->user; if (q2->pred != NULL) HError(3190,"CloneNetwork: Overwriting a pred linkset"); q2->pred = q->pred; } p2 = p2->chain; } if (nu != nx) HError(3190,"CloneNetwork: shared pred linkset count %d vs %d",nx,nu); q->pred->nUse = nu; } } p=p->chain; } clone.entryNode = (Link)prototype.entryNode->user; clone.exitNode = (Link)prototype.exitNode->user; return clone;} /* ------------------------ Variable (SubNet) Defs ------------------- */static SubNetDef *defs;static LabId subNetId;static MemHeap subNetHeap;static void RemoveGlue(HPNetwork *network);/* InitSubNetDefs: set the list of subnet defs to empty */static void InitSubNetDefs(void){ /* SubNetDef * dummy; */ defs = NULL; subNetId = GetLabId("$$$HParse_SubNet",TRUE); CreateHeap(&subNetHeap,"HParse SubNet Heap",MHEAP,sizeof(SubNetDef), 1.5, 1000, 10000); /* dummy = (SubNetDef *) New(&subNetHeap,sizeof(SubNetDef)); */ /* Dispose(&subNetHeap,dummy); */}/* DefineSubNet: define a subnet with given name */static void DefineSubNet(LabId name, Link entryNode, Link exitNode, Link chain){ SubNetDef *p; p=(SubNetDef *)New(&subNetHeap,sizeof(SubNetDef)); p->netName=name; p->network.entryNode = entryNode; p->network.exitNode = exitNode; p->network.chain = chain; RemoveGlue(&(p->network)); p->next = defs; defs = p; /* store pointer to sub network in NameCell */ name->aux = (Ptr) &p->network; }/* FreeSubNetDefs: free all storage used by subnet definitions */static void FreeSubNetDefs(void){ SubNetDef *p; while (defs!=NULL) { FreeNetwork(&defs->network); defs->netName->aux=NULL; /*reset aux NameCell field*/ p=defs->next; defs=p; } ResetHeap(&subNetHeap);}/* ------------ Special Triphone Loop Builder ------------- */typedef struct{ LabId l; LabId r; LabId m;}SplitName;MemHeap joinHeap;MemHeap splitNameHeap;MemHeap subNetStoreHeap;MemHeap jMatHeap;typedef unsigned char **JoinMatrix; static JoinMatrix jmat; /* binary join matrix */static int jmRows,jmCols; /* size of JoinMatrix *//* SplitTriName: splits name n of form A-B+C in to 3 parts if either context is missing then the corresponding part is null */static void SplitTriName(LabId n, SplitName *x){ char buf[64],*p; x->l = x->r = NULL; strcpy(buf,n->name); if ((p=strrchr(buf,'+')) != NULL) { /* Right Context found */ *p++ = '\0'; x->r = GetLabId(p,TRUE); } if ((p=strchr(buf,'-')) != NULL) { /* Left Context found */ *p++ = '\0'; x->m = GetLabId(p,TRUE); x->l = GetLabId(buf,TRUE); } else x->m = GetLabId(buf,TRUE);}/* MakeTriList: split all the elements of a triloop into component parts *//* stores the result in trilist */static SplitName* MakeTriList(int numElements, LinkSet *asucc){ int i; Link thisL; SplitName *trilist; /* reserve space for numElements plus TLOOP_BEGIN & TLOOP_END if not present */ CreateHeap(&splitNameHeap,"HParse Split Name Heap",MHEAP,(numElements+2)*sizeof(SplitName),0,1,1); trilist = (SplitName *) New(&splitNameHeap,(numElements+2)*sizeof(SplitName)); for (i=0;i<numElements;i++){ /* Build split name list */ thisL = asucc->links[i+1]; SplitTriName(thisL->modelName,trilist+i); } return trilist;}/* FindLoopBegin: find the glue node before the loop begins *//* free the LinkSets of the skipped glue nodes */Link FindLoopBegin(Link *hd){ Link a; LinkSet *asucc; a = *hd; while (a->succ->links[1]->modelName == NULL) { FreeLinkSet(a->pred); a->pred = NULL; asucc = a->succ; a->succ = NULL; a = asucc->links[1]; FreeLinkSet(asucc); } return a;} /* FindLoopEnd: find the glue node after the loop ends *//* free the LinkSets of the skipped glue nodes */Link FindLoopEnd(Link *tl){ Link b; LinkSet *bpred; b = *tl; while (b->pred->links[1]->modelName == NULL) { FreeLinkSet(b->succ); b->succ = NULL; bpred = b->pred; b->pred = NULL; b = bpred->links[1]; FreeLinkSet(bpred); } return b;} void SwapSN(SplitName *sn1, SplitName *sn2){ SplitName tmpSN; tmpSN = *sn2; *sn2 = *sn1; *sn1 = tmpSN;} void SwapNodeNames(Link l1, Link l2){ LabId tmpId; tmpId = l2->modelName; l2->modelName = l1->modelName; l1->modelName = tmpId; tmpId = l2->extName; l2->extName = l1->extName; l1->extName = tmpId;}/* AddTLoopBeginEnd: add TLOOP_BEGIN & TLOOP_END if not present *//* make them last elements of loop and trilist *//* return (new) number of elements in loop */int AddTLoopBeginEnd(int numElements, SplitName* trilist, Link a, Link b){ LabId loopBeginId, loopEndId; SplitName *tlb, *tle; Boolean beginFound = FALSE; Boolean endFound = FALSE; int total = numElements; int ib,ie; LinkSet *asucc; Link p; loopBeginId = GetLabId("TLOOP_BEGIN",TRUE); loopEndId = GetLabId("TLOOP_END",TRUE); tlb = trilist; for (ib = 0; ib < numElements; ib++) { tlb = trilist+ib; if (tlb->m == loopBeginId) { beginFound = TRUE; break; } } tle = trilist; for (ie = 0; ie < numElements; ie++) { tle = trilist+ie; if (tle->m == loopEndId) { endFound = TRUE; break; } } if (!beginFound) { p=CreateNode(loopBeginId,&curChain,LINKCHUNKSIZE,LINKCHUNKSIZE); p->extName = loopBeginId; HeadMerge(a, p); TailMerge(p, b); (trilist+total)->m = loopBeginId; (trilist+total)->r = NULL; tlb = trilist+total; ib = total; total++; } if (!endFound) { p=CreateNode(loopEndId,&curChain,LINKCHUNKSIZE,LINKCHUNKSIZE); p->extName = loopEndId; HeadMerge(a, p);
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -