door kee » zo 02 feb 2020, 14:52
Er is inderdaad enige vereenvoudiging mogelijk. Dat brengt je soms een stap verder naar de volgende waarde van N.
Dit is een vereenvoudigde snippet van wat ik nu heb. Je kan zien dat daar deze vereenvoudiging in zit door steeds slechts 1 van alle karakters die nog niet gebruikt waren in de rij tot dan toe te behandelen. In feite maakt een permutatie van alle karakters idd niets uit (rij 58852 is in feite hetzelfde als 12213), maar ik denk dat in het huidige format dat er al min of meer in zit doordat de foreach loop stopt wanneer één keer State.Win wordt teruggegeven.
Het gebruiken van een HashSet waarbij elke twee opeenvolgende karakters worden opgeslaan als een item, ipv een string om in te zoeken, dacht ik zou ook tijdswinst opleveren, maar het steeds opnieuw moeten clonen van de hashset bleek hierin te veel tijd in te nemen (hoewel ik dat toch nog eens opnieuw zou kunnen bekijken of dat niet beter kon).
Volgende dat ik nog kan doen is multithreading gebruiken voor de foreach loop en te stoppen wanneer een van de returns State.Win teruggeeft (idee is hier dat als er een snelle State.Win returned wordt met een later karakter, de vorige karakters, die mss trager tot een resultaat leiden, niet behandeld moeten worden), maar dat moet ik nog eens bekijken wat daar mogelijk is, gezien het ook trager kan zijn doordat je al de berekening start voor alle karakters, wat mss niet nodig is. Voor N=7 is het trouwens opnieuw speler2 die de winnende strategie heeft.
Code: Selecteer alles
private string Characters;
private void ButtonGo_Click(object sender, EventArgs e)
{
Characters = "123456";
Messages.ShowMessage(CalculateState(" ", Characters[0]).ToString())
}
private State CalculateState(string written, char character)
{
if (written[written.Length - 2] == character)
return State.LooseNow;
string search = string.Concat(written[written.Length - 1], character);
if (written.Contains(search))
return State.LooseNow;
written = written + character;
bool noneHandled = false;
foreach (char ch in Characters)
{
if (!written.Contains(ch))
if (noneHandled)
continue;
else
noneHandled = true;
if (CalculateState(written, ch) == State.Win)
return State.LooseFuture;
}
return State.Win;
}
Er is inderdaad enige vereenvoudiging mogelijk. Dat brengt je soms een stap verder naar de volgende waarde van N.
Dit is een vereenvoudigde snippet van wat ik nu heb. Je kan zien dat daar deze vereenvoudiging in zit door steeds slechts 1 van alle karakters die nog niet gebruikt waren in de rij tot dan toe te behandelen. In feite maakt een permutatie van alle karakters idd niets uit (rij 58852 is in feite hetzelfde als 12213), maar ik denk dat in het huidige format dat er al min of meer in zit doordat de foreach loop stopt wanneer één keer State.Win wordt teruggegeven.
Het gebruiken van een HashSet waarbij elke twee opeenvolgende karakters worden opgeslaan als een item, ipv een string om in te zoeken, dacht ik zou ook tijdswinst opleveren, maar het steeds opnieuw moeten clonen van de hashset bleek hierin te veel tijd in te nemen (hoewel ik dat toch nog eens opnieuw zou kunnen bekijken of dat niet beter kon).
Volgende dat ik nog kan doen is multithreading gebruiken voor de foreach loop en te stoppen wanneer een van de returns State.Win teruggeeft (idee is hier dat als er een snelle State.Win returned wordt met een later karakter, de vorige karakters, die mss trager tot een resultaat leiden, niet behandeld moeten worden), maar dat moet ik nog eens bekijken wat daar mogelijk is, gezien het ook trager kan zijn doordat je al de berekening start voor alle karakters, wat mss niet nodig is. Voor N=7 is het trouwens opnieuw speler2 die de winnende strategie heeft.
[code]
private string Characters;
private void ButtonGo_Click(object sender, EventArgs e)
{
Characters = "123456";
Messages.ShowMessage(CalculateState(" ", Characters[0]).ToString())
}
private State CalculateState(string written, char character)
{
if (written[written.Length - 2] == character)
return State.LooseNow;
string search = string.Concat(written[written.Length - 1], character);
if (written.Contains(search))
return State.LooseNow;
written = written + character;
bool noneHandled = false;
foreach (char ch in Characters)
{
if (!written.Contains(ch))
if (noneHandled)
continue;
else
noneHandled = true;
if (CalculateState(written, ch) == State.Win)
return State.LooseFuture;
}
return State.Win;
}
[/code]