efgfunc.cc
来自「Gambit 是一个游戏库理论软件」· CC 代码 · 共 1,499 行 · 第 1/3 页
CC
1,499 行
//-------------// WriteSequenceForm//-------------static Portion *GSM_WriteSfg(GSM &, Portion **param){ gOutput &out = ((OutputPortion*) param[0])->Value(); const efgGame *efg = ((EfgPortion*) param[1])->Value(); if (!IsPerfectRecall(*efg)) throw gclRuntimeError("Sequence form not defined for game of imperfect recall"); EFSupport efs(*efg); Sfg sfg(efs); sfg.Dump(out); return param[0]->ValCopy();}//-------------// SequenceForm//-------------void Recurse_Sfg(ListPortion *por, int pl, const Sfg &sfg, gIndexOdometer &index){ if(pl >=1 ) for(int j=1;j<=sfg.NumSequences(pl);j++) { ListPortion *p = new ListPortion; Recurse_Sfg(p,pl-1,sfg,index); por->Append(p); } else { index.Turn(); for (int i = 1; i <= sfg.NumPlayers(); i++) por->Append(new NumberPortion(sfg.Payoff(index.CurrentIndices(),i))); }}static Portion *GSM_Sfg(GSM &, Portion **param){ const efgGame *efg = ((EfgPortion*) param[0])->Value(); if (!IsPerfectRecall(*efg)) throw gclRuntimeError("Sequence form not defined for game of imperfect recall"); EFSupport efs(*efg); Sfg sfg(efs); ListPortion *por = new ListPortion; gIndexOdometer index(sfg.NumSequences()); Recurse_Sfg(por,sfg.NumPlayers(),sfg,index); return por;}static Portion *GSM_SfgStrats(GSM &, Portion **param){ const efgGame *efg = ((EfgPortion*) param[0])->Value(); if (!IsPerfectRecall(*efg)) throw gclRuntimeError("Sequence form not defined for game of imperfect recall"); EFPlayer *pl = ((EfPlayerPortion*) param[1])->Value(); int p = pl->GetNumber(); EFSupport efs(*efg); Sfg sfg(efs); ListPortion *por = new ListPortion; for (int i=1;i<=sfg.NumSequences(p);i++) { gList<const Action *> h((sfg.GetSequence(p,i))->History()); ListPortion *por1 = new ListPortion; for(int j=1;j<=h.Length();j++) por1->Append(new ActionPortion((Action *)h[j])); por->Append(por1); } return por; }static Portion *GSM_SfgConstraints(GSM &, Portion **param){ const efgGame *efg = ((EfgPortion*) param[0])->Value(); if (!IsPerfectRecall(*efg)) throw gclRuntimeError("Sequence form not defined for game of imperfect recall"); EFPlayer *pl = ((EfPlayerPortion*) param[1])->Value(); int p = pl->GetNumber(); EFSupport efs(*efg); Sfg sfg(efs); gRectArray<gNumber> A(sfg.Constraints(p)); ListPortion *por = new ListPortion; for(int i=A.MinRow();i<=A.MaxRow();i++) { ListPortion *p1 = new ListPortion; for(int j=A.MinCol();j<=A.MaxCol();j++) p1->Append(new NumberPortion(A(i,j))); por->Append(p1); } return por;}/* #include "seqform.h" #include "seqform.imp" static Portion *GSM_SfgTableau(GSM &, Portion **param) { EFSupport *efs = ((EfSupportPortion*) param[0])->Value(); SeqFormParams prm; SeqFormModule<gNumber> sfm(*efs,prm); gMatrix<gNumber> A(sfm.GetA()); ListPortion *por = new ListPortion; for(int i=A.MinRow();i<=A.MaxRow();i++) { ListPortion *p1 = new ListPortion; for(int j=A.MinCol();j<=A.MaxCol();j++) p1->Append(new NumberPortion(A(i,j))); por->Append(p1); } return por; }*///-------------------// SetChanceProbs//-------------------static Portion *GSM_SetChanceProbs(GSM &gsm, Portion **param){ Infoset *s = ((InfosetPortion *) param[0])->Value(); ListPortion *p = (ListPortion *) param[1]; efgGame *efg = s->Game(); if (!s->GetPlayer()->IsChance()) throw gclRuntimeError("Information set does not belong to chance player"); for (int i = 1; i <= p->Length(); i++) efg->SetChanceProb(s, i, ((NumberPortion *) (*p)[i])->Value()); gsm.InvalidateGameProfile(s->Game(), true); return new InfosetPortion(s);}//-------------// SetComment//-------------static Portion *GSM_SetComment(GSM &, Portion **param){ efgGame *efg = ((EfgPortion *) param[0])->Value(); gText comment = ((TextPortion *) param[1])->Value(); efg->SetComment(comment); return param[0]->ValCopy();}//--------------// SetName//--------------static Portion *GSM_SetName(GSM &, Portion **param){ gText name(((TextPortion *) param[1])->Value()); switch (param[0]->Spec().Type) { case porACTION: (((ActionPortion *) param[0])->Value())->SetName(name); break; case porINFOSET: ((InfosetPortion *) param[0])->Value()->SetName(name); break; case porNODE: ((NodePortion *) param[0])->Value()->SetName(name); break; case porEFOUTCOME: ((EfOutcomePortion *) param[0])->Value()->GetGame()->SetOutcomeName(((EfOutcomePortion *) param[0])->Value(), name); break; case porEFPLAYER: ((EfPlayerPortion *) param[0])->Value()->SetName(name); break; case porEFSUPPORT: ((EfSupportPortion *) param[0])->Value()->SetName(name); break; case porEFG: ((EfgPortion *) param[0])->Value()->SetTitle(name); break; default: throw gclRuntimeError("Bad type passed to SetName[]"); } return param[0]->ValCopy();}//----------------// SetOutcome//----------------static Portion *GSM_SetOutcome(GSM &gsm, Portion **param){ Node *n = ((NodePortion *) param[0])->Value(); efgOutcome *outcome = ((EfOutcomePortion *) param[1])->Value(); if (outcome) { outcome->GetGame()->SetOutcome(n, outcome); gsm.InvalidateGameProfile(n->Game(), true); return new EfOutcomePortion(outcome); } else { return new NullPortion(porEFOUTCOME); }}//----------------// SetPayoff//----------------static Portion *GSM_SetPayoff(GSM &gsm, Portion **param){ efgOutcome *outcome = ((EfOutcomePortion *) param[0])->Value(); EFPlayer *player = ((EfPlayerPortion *) param[1])->Value(); efgGame *efg = player->Game(); gNumber value = ((NumberPortion *) param[2])->Value(); efg->SetPayoff(outcome, player->GetNumber(), value); gsm.InvalidateGameProfile(outcome->GetGame(), true); return param[0]->ValCopy();}//----------------// Subgames//----------------static Portion *GSM_Subgames(GSM &, Portion **param){ efgGame &E = *((EfgPortion*) param[0])->Value(); gList<Node *> list; LegalSubgameRoots(E, list); Portion *por = ArrayToList(list); return por; } //--------------// Support//--------------static Portion *GSM_Support(GSM &, Portion **param){ efgGame &E = * ((EfgPortion *) param[0])->Value(); Portion *por = new EfSupportPortion(new EFSupport(E)); return por;}//--------------// EFBasis//--------------static Portion *GSM_Basis(GSM &, Portion **param){ efgGame &E = * ((EfgPortion *) param[0])->Value(); Portion *por = new EfBasisPortion(new EFBasis(E)); return por;}//--------------// UnDominated//--------------static Portion *GSM_UnDominated(GSM &gsm, Portion **param){ EFSupport *S = ((EfSupportPortion *) param[0])->Value(); bool strong = ((BoolPortion *) param[1])->Value(); bool conditional = ((BoolPortion *) param[2])->Value(); gWatch watch; gBlock<int> players(S->GetGame().NumPlayers()); for (int i = 1; i <= players.Length(); i++) players[i] = i; EFSupport T(S->Undominated(strong, conditional, players, ((OutputPortion *) param[4])->Value(), gsm.GetStatusMonitor())); ((NumberPortion *) param[3])->SetValue(watch.Elapsed()); return new EfSupportPortion(new EFSupport(T));}//-----------------// UnMarkSubgame//-----------------static Portion *GSM_UnMarkSubgame(GSM &, Portion **param){ Node *n = ((NodePortion *) param[0])->Value(); n->Game()->UnmarkSubgame(n); return new NodePortion(n);}void Init_efgfunc(GSM *gsm){ gclFunction *FuncObj; static struct { char *sig; Portion *(*func)(GSM &, Portion **); } ftable[] = { { "Actions[infoset->INFOSET*, support->EFSUPPORT] =: LIST(ACTION)", GSM_Actions }, { "Actions[infoset->INFOSET*, basis->EFBASIS] =: LIST(ACTION)", GSM_BasisActions }, { "ActionNumber[action->ACTION, sup->EFSUPPORT] =: INTEGER", GSM_ActionNumber }, { "ActionNumber[action->ACTION, basis->EFBASIS] =: INTEGER", GSM_BasisActionNumber }, { "AddAction[support->EFSUPPORT, action->ACTION] =: EFSUPPORT", GSM_AddAction }, { "AddAction[basis->EFBASIS, action->ACTION] =: EFBASIS", GSM_AddBasisAction }, { "AddMove[infoset->INFOSET, node->NODE] =: NODE", GSM_AddMove }, { "AddNode[basis->EFBASIS, node->NODE] =: EFBASIS", GSM_AddBasisNode }, { "Chance[efg->EFG] =: EFPLAYER", GSM_Chance }, { "ChanceProb[action->ACTION] =: NUMBER", GSM_ChanceProb }, { "Children[node->NODE] =: LIST(NODE)", GSM_Children }, { "Comment[efg->EFG] =: TEXT", GSM_Comment }, { "CompressEfg[support->EFSUPPORT] =: EFG", GSM_CompressEfg }, { "CopyTree[from->NODE, to->NODE] =: NODE", GSM_CopyTree }, { "DeleteAction[action->ACTION] =: INFOSET", GSM_DeleteAction }, { "DeleteEmptyInfoset[infoset->INFOSET] =: BOOLEAN", GSM_DeleteEmptyInfoset }, { "DeleteMove[node->NODE, keep->NODE] =: NODE", GSM_DeleteMove }, { "DeleteOutcome[outcome->EFOUTCOME] =: LIST(NODE)", GSM_DeleteOutcome }, { "DeleteTree[node->NODE] =: NODE", GSM_DeleteTree }, { "Game[player->EFPLAYER] =: EFG", GSM_Game_EfgElements }, { "Game[node->NODE] =: EFG", GSM_Game_EfgElements }, { "Game[outcome->EFOUTCOME] =: EFG", GSM_Game_EfgElements }, { "Game[infoset->INFOSET] =: EFG", GSM_Game_EfgElements }, { "Infoset[node->NODE*] =: INFOSET", GSM_Infoset_Node }, { "Infoset[action->ACTION*] =: INFOSET", GSM_Infoset_Action }, { "Infosets[player->EFPLAYER] =: LIST(INFOSET)", GSM_Infosets }, { "InsertAction[infoset->INFOSET] =: ACTION", GSM_InsertAction }, { "InsertAction[infoset->INFOSET, at->ACTION] =: ACTION", GSM_InsertActionAt }, { "InsertMove[infoset->INFOSET, node->NODE] =: NODE", GSM_InsertMove }, { "IsConsistent[basis->EFBASIS] =: BOOLEAN", GSM_IsBasisConsistent }, { "IsConstSum[efg->EFG] =: BOOLEAN", GSM_IsConstSum }, { "IsPerfectRecall[efg->EFG] =: BOOLEAN", GSM_IsPerfectRecall }, { "IsPredecessor[node->NODE, of->NODE] =: BOOLEAN", GSM_IsPredecessor }, { "IsSuccessor[node->NODE, from->NODE] =: BOOLEAN", GSM_IsSuccessor }, { "LoadEfg[file->TEXT] =: EFG", GSM_LoadEfg }, { "MarkSubgame[node->NODE] =: BOOLEAN", GSM_MarkSubgame }, { "MarkedSubgame[node->NODE] =: BOOLEAN", GSM_MarkedSubgame }, { "Members[infoset->INFOSET*] =: LIST(NODE)", GSM_Members }, { "MergeInfosets[to->INFOSET, from->INFOSET] =: INFOSET", GSM_MergeInfosets }, { "MoveToInfoset[node->NODE, infoset->INFOSET] =: NODE", GSM_MoveToInfoset }, { "MoveTree[from->NODE, to->NODE] =: NODE", GSM_MoveTree }, { "Name[x->ACTION*] =: TEXT", GSM_Name }, { "Name[x->INFOSET*] =: TEXT", GSM_Name }, { "Name[x->NODE*] =: TEXT", GSM_Name }, { "Name[x->EFOUTCOME*] =: TEXT", GSM_Name }, { "Name[x->EFPLAYER*] =: TEXT", GSM_Name }, { "Name[x->EFSUPPORT*] =: TEXT", GSM_Name }, { "Name[x->EFG*] =: TEXT", GSM_Name }, { "NewInfoset[player->EFPLAYER, actions->NUMBER] =: INFOSET", GSM_NewInfoset }, { "NewOutcome[efg->EFG] =: EFOUTCOME", GSM_NewOutcome }, { "NewPlayer[efg->EFG] =: EFPLAYER", GSM_NewPlayer }, { "NextSibling[node->NODE] =: NODE", GSM_NextSibling }, { "Nodes[efg->EFG] =: LIST(NODE)", GSM_Nodes }, { "Nodes[infoset->INFOSET*, basis->EFBASIS] =: LIST(NODE)", GSM_BasisNodes }, { "NodeNumber[node->NODE, basis->EFBASIS] =: INTEGER", GSM_BasisNodeNumber }, { "NthChild[node->NODE, n->INTEGER] =: NODE", GSM_NthChild }, { "Outcome[node->NODE*] =: EFOUTCOME", GSM_Outcome }, { "Outcomes[efg->EFG] =: LIST(EFOUTCOME)", GSM_Outcomes }, { "Parent[node->NODE*] =: NODE", GSM_Parent }, { "Payoff[outcome->EFOUTCOME*, player->EFPLAYER] =: NUMBER", GSM_Payoff }, { "Player[infoset->INFOSET*] =: EFPLAYER", GSM_Player }, { "Players[efg->EFG] =: LIST(EFPLAYER)", GSM_Players }, { "PriorAction[node->NODE] =: ACTION", GSM_PriorAction }, { "PriorSibling[node->NODE] =: NODE", GSM_PriorSibling }, { "RemoveAction[support->EFSUPPORT, action->ACTION] =: EFSUPPORT", GSM_RemoveAction }, { "RemoveAction[support->EFBASIS, action->ACTION] =: EFBASIS", GSM_RemoveBasisAction }, { "RemoveNode[support->EFBASIS, node->NODE] =: EFBASIS", GSM_RemoveBasisNode }, { "Reveal[infoset->INFOSET, who->LIST(EFPLAYER)] =: INFOSET", GSM_Reveal }, { "RootNode[efg->EFG] =: NODE", GSM_RootNode }, { "SaveEfg[efg->EFG, file->TEXT] =: EFG", GSM_SaveEfg }, { "SetChanceProbs[infoset->INFOSET, probs->LIST(NUMBER)] =: INFOSET", GSM_SetChanceProbs }, { "SetComment[efg->EFG, comment->TEXT] =: EFG", GSM_SetComment }, { "SetName[x->ACTION, name->TEXT] =: ACTION", GSM_SetName }, { "SetName[x->INFOSET, name->TEXT] =: INFOSET", GSM_SetName }, { "SetName[x->NODE, name->TEXT] =: NODE", GSM_SetName }, { "SetName[x->EFOUTCOME, name->TEXT] =: EFOUTCOME", GSM_SetName }, { "SetName[x->EFPLAYER, name->TEXT] =: EFPLAYER", GSM_SetName }, { "SetName[x->EFSUPPORT, name->TEXT] =: EFSUPPORT", GSM_SetName }, { "SetName[x->EFG, name->TEXT] =: EFG", GSM_SetName }, { "SetOutcome[node->NODE, outcome->EFOUTCOME*] =: EFOUTCOME", GSM_SetOutcome }, { "SetPayoff[outcome->EFOUTCOME, player->EFPLAYER, payoff->NUMBER] =: EFOUTCOME", GSM_SetPayoff }, { "Subgames[efg->EFG] =: LIST(NODE)", GSM_Subgames }, { "Support[efg->EFG] =: EFSUPPORT", GSM_Support }, { "Basis[efg->EFG] =: EFBASIS", GSM_Basis }, { "UnMarkSubgame[node->NODE] =: NODE", GSM_UnMarkSubgame }, { "PossibleNashSupports[efg->EFG] =: LIST(EFSUPPORT)", GSM_PossibleNashSupports }, { 0, 0 } }; for (int i = 0; ftable[i].sig != 0; i++) { gsm->AddFunction(new gclFunction(*gsm, ftable[i].sig, ftable[i].func, funcLISTABLE | funcGAMEMATCH)); } FuncObj = new gclFunction(*gsm, "UnDominated", 1); FuncObj->SetFuncInfo(0, gclSignature(GSM_UnDominated, porEFSUPPORT, 6)); FuncObj->SetParamInfo(0, 0, gclParameter("support", porEFSUPPORT)); FuncObj->SetParamInfo(0, 1, gclParameter("strong", porBOOLEAN, new BoolPortion(false))); FuncObj->SetParamInfo(0, 2, gclParameter("conditional", porBOOLEAN, new BoolPortion(false))); FuncObj->SetParamInfo(0, 3, gclParameter("time", porNUMBER, new NumberPortion(0.0), BYREF)); FuncObj->SetParamInfo(0, 4, gclParameter("traceFile", porOUTPUT, new OutputPortion(*new gNullOutput), BYREF)); FuncObj->SetParamInfo(0, 5, gclParameter("traceLevel", porNUMBER, new NumberPortion(0))); gsm->AddFunction(FuncObj); FuncObj = new gclFunction(*gsm, "IsDominated", 1); FuncObj->SetFuncInfo(0, gclSignature(GSM_IsDominated_Efg, porBOOLEAN, 7)); FuncObj->SetParamInfo(0, 0, gclParameter("action", porACTION)); FuncObj->SetParamInfo(0, 1, gclParameter("support", porEFSUPPORT)); FuncObj->SetParamInfo(0, 2, gclParameter("strong", porBOOLEAN, new BoolPortion(false))); FuncObj->SetParamInfo(0, 3, gclParameter("conditional", porBOOLEAN, new BoolPortion(false))); FuncObj->SetParamInfo(0, 4, gclParameter("time", porNUMBER, new NumberPortion(0.0), BYREF)); FuncObj->SetParamInfo(0, 5, gclParameter("traceFile", porOUTPUT, new OutputPortion(*new gNullOutput), BYREF)); FuncObj->SetParamInfo(0, 6, gclParameter("traceLevel", porNUMBER, new NumberPortion(0))); gsm->AddFunction(FuncObj); // Adding NewEfg FuncObj = new gclFunction(*gsm, "NewEfg", 1); FuncObj->SetFuncInfo(0, gclSignature(GSM_NewEfg, porEFG, 1)); FuncObj->SetParamInfo(0, 0, gclParameter("players", PortionSpec(porTEXT,1), new ListPortion)); gsm->AddFunction(FuncObj); // Adding WriteSequenceForm FuncObj = new gclFunction(*gsm, "WriteSequenceForm", 1); FuncObj->SetFuncInfo(0, gclSignature(GSM_WriteSfg, porOUTPUT, 2, 0 , funcNONLISTABLE)); FuncObj->SetParamInfo(0, 0, gclParameter("output", porOUTPUT, REQUIRED, BYREF)); FuncObj->SetParamInfo(0, 1, gclParameter("efg", porEFG)); gsm->AddFunction(FuncObj); FuncObj = new gclFunction(*gsm, "SequenceForm", 1); FuncObj->SetFuncInfo(0, gclSignature(GSM_Sfg, PortionSpec(porNUMBER, NLIST), 1)); FuncObj->SetParamInfo(0, 0, gclParameter("efg", porEFG)); gsm->AddFunction(FuncObj); FuncObj = new gclFunction(*gsm, "SequenceFormStrats", 1); FuncObj->SetFuncInfo(0, gclSignature(GSM_SfgStrats, PortionSpec(porACTION, 2), 2)); FuncObj->SetParamInfo(0, 0, gclParameter("efg", porEFG)); FuncObj->SetParamInfo(0, 1, gclParameter("player", porEFPLAYER)); gsm->AddFunction(FuncObj); FuncObj = new gclFunction(*gsm, "SequenceFormConstraints", 1); FuncObj->SetFuncInfo(0, gclSignature(GSM_SfgConstraints, PortionSpec(porNUMBER, 2), 2)); FuncObj->SetParamInfo(0, 0, gclParameter("efg", porEFG)); FuncObj->SetParamInfo(0, 1, gclParameter("player", porEFPLAYER)); gsm->AddFunction(FuncObj); /* FuncObj = new gclFunction(*gsm, "SequenceFormTableau", 1); FuncObj->SetFuncInfo(0, gclSignature(GSM_SfgTableau, PortionSpec(porNUMBER, 2), 1)); FuncObj->SetParamInfo(0, 0, gclParameter("support", porEFSUPPORT)); gsm->AddFunction(FuncObj); */}
⌨️ 快捷键说明
复制代码Ctrl + C
搜索代码Ctrl + F
全屏模式F11
增大字号Ctrl + =
减小字号Ctrl + -
显示快捷键?