Laden...

Feststellen, wenn Index grösser als Anzahl der Items in der Liste ist & letztes Element zurückgeben

Erstellt von elTorito vor 8 Jahren Letzter Beitrag vor 8 Jahren 1.697 Views
elTorito Themenstarter:in
177 Beiträge seit 2009
vor 8 Jahren
Feststellen, wenn Index grösser als Anzahl der Items in der Liste ist & letztes Element zurückgeben

Guten Morgen,

ich habe 2 Listen:


 public static List<int> XATCSortedNumbers = new List<int>()
{
{1},
{2},
....
{19},
{20},
{25}
};

 public static List<int> XATCRandomNumbers = new List<int>()
{
{25},    
{20},
{1},
{18},
{4},
{13},
....
{9},
{12},
{5},
};

Und folgenden Helfer um dort ein passenden wert zu bekommen:


public static class Helperlein
    {
        public static T NextOf<T>(this IList<T> list, T item)
        {
            return list[(list.IndexOf(item) + 1) == list.Count ? 0 : (list.IndexOf(item) + 1)];
        }
        public static T Next2Of<T>(this IList<T> list, T item)
        {
            return list[(list.IndexOf(item) + 2) >= list.Count ? 0 : (list.IndexOf(item) + 2)];
        }
        public static T Next3Of<T>(this IList<T> list, T item)
        {
            return list[(list.IndexOf(item) + 3) >= list.Count ? 0 : (list.IndexOf(item) + 3)];
        }
    }

Und folgende Funktion welche auf den passenden Helferlein verweist:


 public int GetNextNoToHit(int currHitNo, HitTarget hittarget, XATCPerson p)
        {
            int nextNo = 0;
            if (_atcDirection == ATCDirection.Numerical)
            {
                if (_atcSpeed == ATCSpeed.Slow)
                {
                    ///Next sorted 
                    nextNo = MyDictionary.XATCSortedNumbers.NextOf(currHitNo);
                }
                else if (_atcSpeed == ATCSpeed.Fast)
                {
                    //Next sorted +2 or +3 
                    if (hittarget == HitTarget.Single)
                    {
                        nextNo = MyDictionary.XATCSortedNumbers.NextOf(currHitNo);
                    }
                    else if (hittarget == HitTarget.Double)
                    {
                        nextNo = MyDictionary.XATCSortedNumbers.Next2Of(currHitNo);
                    } 
                    else if (hittarget == HitTarget.Triple)
                    {
                        nextNo = MyDictionary.XATCSortedNumbers.Next3Of(currHitNo);
                    }
                }
                
            }
            else if (_atcDirection == ATCDirection.Random)
            {
                if (_atcSpeed == ATCSpeed.Slow)
                {
                    // Next Random Nummer 
                    nextNo = MyDictionary.XATCRandomNumbers.NextOf(currHitNo);
                }
                else if (_atcSpeed == ATCSpeed.Fast)
                {
                    //Next sorted +2 or +3 
                    if (hittarget == HitTarget.Single)
                    {
                        nextNo = MyDictionary.XATCRandomNumbers.NextOf(currHitNo);
                    }
                    if (hittarget == HitTarget.Double)
                    {
                        nextNo = MyDictionary.XATCRandomNumbers.Next2Of(currHitNo);
                    }
                    else if (hittarget == HitTarget.Triple)
                    {
                        nextNo = MyDictionary.XATCRandomNumbers.Next3Of(currHitNo);
                    }
                }
            }

            return nextNo;
        }

Ziel ist die letzte Zahl der Liste, wenn nextNo = letzte Zahl, Ziel erreicht, für NextOf passt das, da einer Schritte, stehe ich aber bei XATCSortedNumbers auf 19, und HitTarget ist Triple, bekomme ich 1 zurück.

Wie könnte ich das elegant lösen, dass wenn Next2Of oder Next3Of über das Ende hinaus gehen, ich die letzte Zahl der Liste zurückbekomme?.

ich hatte erst gedacht über IndexOf prüfen, aber damit hätte ich Probleme wenn schon beim Start weil Index von nextNo immer kleiner ist als FinalNo:


else if (hittarget == HitTarget.Triple)
                    {
                        nextNo = MyDictionary.XATCRandomNumbers.Next3Of(currHitNo);
                        if (MyDictionary.XATCRandomNumbers.IndexOf(nextNo) < MyDictionary.XATCRandomNumbers.IndexOf(GetFinalNo()))
                        {

                        }
                        
                    }

Hat jemand ein Denkanstoß für mich.? 8)

Vielen Dank

2.207 Beiträge seit 2011
vor 8 Jahren

Hallo elTorito,

dein Beitrag ist aufgrund solcher Sätze

Ziel ist die letzte Zahl der Liste, wenn nextNo = letzte Zahl, Ziel erreicht, für NextOf
passt das, da einer Schritte, stehe ich aber bei XATCSortedNumbers auf 19, und HitTarget ist Triple, bekomme ich 1 zurück.

echt nicht einfach zu lesen und zu verstehen. Wie dem auch sei: Möchtest du, bevor du das (zweit/dritt)-nächste Item von der Liste zurückgibst feststellen, ob es überhaupt ein zweit- oder drittnächstes gibt? Wenn ja --> gib das zurück, wenn nein --> gib das letzte der Liste zurück.

Beschreibt das dein Problem?

Ich habe auchmal den Titel angepasst, so wie ich meinte, dass er richtig ist. Wenn das besser geht oder falsch ist, korrigier es bitte.

Gruss

Coffeebean

3.003 Beiträge seit 2006
vor 8 Jahren

Zuerst einmal muss dir doch auffallen, dass du drei NextOf-Methoden hast, die alle dasselbe tun, nur mit einem Parameter.

Zum zweiten:


int Example(List<int> numberList, int stride)
{
      var resultList = numberList.Skip(stride);
      return resultList.Count() > 0 ? resultList.First() : numberList.Last();
}

Nur als Ansatz.

LaTino
Und als Anmerkung, deine Art, mit Daten umzugehen, bewegt sich nah an der Grenze zur obfuscation.

"Furlow, is it always about money?"
"Is there anything else? I mean, how much sex can you have?"
"Don't know. I haven't maxed out yet."
(Furlow & Crichton, Farscape)

elTorito Themenstarter:in
177 Beiträge seit 2009
vor 8 Jahren

Möchtest du, bevor du das (zweit/dritt)-nächste Item von der Liste zurückgibst feststellen, ob es überhaupt ein zweit- oder drittnächstes gibt? Wenn ja --> gib das zurück, wenn nein --> gib das letzte der Liste zurück.

Beschreibt das dein Problem?

Hallo CoffeBean,

sorry erstmal für meine Ausdrucksweise, fällt mir manchmal schwer zu Beschreiben was dass Problem ist (Ausser dass ich kommata nicht kann X()

Deine Vermutung passt. Bevor ich das zweit/dritt nächste Element von der Liste hole, soll geprüft werden ob es ein solches gibt, wenn nicht, dann letztes Item zurückgeben.

@Latino, ja ist mir aufgefallen. Hab ich extra so genannt erstmal , weil ich durcheinander kam wann ich welchen Schritt übergab.

Mir ist nun auch aufgefallen dass ich wenn item + x größer als Anzahl der Items in der Liste ist, ich das erste Item zurückgebe, hier muss ich eigentlich nur das letzte Item zurückgeben.

Ja, sorry, ist so eine Macke von mir, ich entwickel meistens drauf los, und Räume erst später den Code auf, und bennene dann die Methoden und klassen um, gucke wo ich noch was optimieren kann, füge Kommentare hinzu... ist mir denke ich klar das ein guter Programmierer (was ich nicht bin) das vorweg schon mit erledigt, und so, einige Fragen / Probleme wahrscheinlich erst gar nicht entstehen würden.

Vielen Dank für euren Denkanstoß

3.003 Beiträge seit 2006
vor 8 Jahren

Was mir im Nachhinein noch auffällt - für verschiedene Akteure unterschiedlich schnelle oder ganz unterschiedliche Arten der Fortbewegung zu implementieren, schreit ein bisschen nach Strategy Pattern. Dürfte bei der Organisation deines Codes hilfreich sein.

LaTino

"Furlow, is it always about money?"
"Is there anything else? I mean, how much sex can you have?"
"Don't know. I haven't maxed out yet."
(Furlow & Crichton, Farscape)

elTorito Themenstarter:in
177 Beiträge seit 2009
vor 8 Jahren

Was mir im Nachhinein noch auffällt - für verschiedene Akteure unterschiedlich schnelle oder ganz unterschiedliche Arten der Fortbewegung zu implementieren, schreit ein bisschen nach
>
. Dürfte bei der Organisation deines Codes hilfreich sein.
LaTino

Hallo Latino,

danke für den Verweis auf das Muster. So ähnlich? habe ich es versucht umzusetzen, ich habe eine Basis Klasse Game, welche die ganzen Basis Funktionen beinhaltet, Spieler hinzufügen, bearbeiten, löschen, Start / Ende, und jedes Spiel (es geht um ein Darts Spiel) hat die gleiche Vorgehensweise, es sind immer 3 Darts pro Runde. Alles was darüber hinausgeht habe ich in einer eigenen Klasse ausgegliedert:


public class ATCGame : Game<ATCUserControl>, IGameAroundTheClock
{
...
}

Hier kommen dann die Logiken der verschiedenen Spielarten rein. Wobei ein Spiel selber so Einstellbar sein kann dass es im Grunde doch wieder ein anderes Spiel ist (also wie du jetzt sagst die Fortbewegung mal langsam mal schnell)

In meinen Falle gerade: Eine einfache Zahl getroffen, geht zur nächsten Zahl auf der Dartscheibe, trifft man Doppel/Trippel darf man 2 oder 3 weiter.

Ich guck mir das nochmal an, Code verschönern und vereinfachen (und lesbarer machen) geht fast immer 😃

Danke.

3.003 Beiträge seit 2006
vor 8 Jahren

So, wie ich mir die Implementierung vorstelle, würde das Ergebnis ungefähr so aussehen:


IGameStrategy nextTargetToHitStrategy = new NotSureAboutTheNameStrategyFactory(_atcDirection, _atcSpeed, hittarget).GetStrategy();
return nextTargetToHitStrategy.CalculateNextNumber(currHitNo);

LaTino

"Furlow, is it always about money?"
"Is there anything else? I mean, how much sex can you have?"
"Don't know. I haven't maxed out yet."
(Furlow & Crichton, Farscape)

elTorito Themenstarter:in
177 Beiträge seit 2009
vor 8 Jahren
  
IGameStrategy nextTargetToHitStrategy = new NotSureAboutTheNameStrategyFactory(_atcDirection, _atcSpeed, hittarget).GetStrategy();  
return nextTargetToHitStrategy.CalculateNextNumber(currHitNo);  
  

Ich versuch das mal. Vielen Dank für das zeigen.

Hinweis von Coffeebean vor 8 Jahren

Keine Full-Quotes bitte. [Hinweis] Wie poste ich richtig? Punkt 2.3

elTorito Themenstarter:in
177 Beiträge seit 2009
vor 8 Jahren

so z.B.: ?


   #region Strategy interface
    public interface IXATCStrategy
    {
        int CalculateNextNumber(int currHitNo);
        ATCGameType GameType { get; set; }
        ATCDirection Direction { get; set; }
        ATCSpeed Speed { get; set; }
        bool PlayWithBull { get; set; }
        HitTarget HittedTarget {get;set;}
    }
    #endregion


    public class NextTargetToHitStrategy
    {
        private ATCGameType _gametype;
        private ATCDirection _direction;
        private ATCSpeed _speed;
        bool _playWithBull;
        private HitTarget _hittedTarget;

        public NextTargetToHitStrategy(ATCGameType gameType, ATCDirection direction, ATCSpeed speed, bool playWithBull, HitTarget hittedTarget)
        {
            this._gametype = gameType;
            this._direction = direction;
            this._speed = speed;
            this._playWithBull = playWithBull;
            this._hittedTarget = hittedTarget;
        }

        public IXATCStrategy GetStrategory()
        {
            IXATCStrategy selectedStrategy = null;
            
            if (_direction == ATCDirection.Numerical)
            {
                if (_speed == ATCSpeed.Slow)
                {
                    selectedStrategy = new NumericalSlow();
                }
                else if (_speed == ATCSpeed.Fast)
                {
                    selectedStrategy = new NumericalFast();
                }

            }
            else if (_direction == ATCDirection.Random)
            {
                if (_speed == ATCSpeed.Slow)
                {
                    selectedStrategy = new RandomSlow();
                }
                else if (_speed == ATCSpeed.Fast)
                {
                    selectedStrategy = new RandomFast();
                }
            }
            selectedStrategy.GameType = _gametype;
            selectedStrategy.Direction = _direction;
            selectedStrategy.Speed = _speed;
            selectedStrategy.PlayWithBull = _playWithBull;
            selectedStrategy.HittedTarget = _hittedTarget;
            return selectedStrategy;
        } 

    }

    class NumericalSlow : IXATCStrategy
    {
        private List<int> list = MyDictionary.XATCSortedNumbers;
        public ATCGameType GameType { get; set; }
        public ATCDirection Direction { get; set; }
        public ATCSpeed Speed { get; set; }
        public bool PlayWithBull { get; set; }
        public HitTarget HittedTarget { get; set; }

        public int CalculateNextNumber(int currHitNo)
        {
            return 0;
        }
    }

    class NumericalFast : IXATCStrategy
    {
        private List<int> list = MyDictionary.XATCSortedNumbers;
        public ATCGameType GameType { get; set; }
        public ATCDirection Direction { get; set; }
        public ATCSpeed Speed { get; set; }
        public bool PlayWithBull { get; set; }
        public HitTarget HittedTarget { get; set; }

        public int CalculateNextNumber(int currHitNo)
        {
            return 0;
        }
    }

    class RandomSlow : IXATCStrategy
    {
        private List<int> list = MyDictionary.XATCRandomNumbers;
        public ATCGameType GameType { get; set; }
        public ATCDirection Direction { get; set; }
        public ATCSpeed Speed { get; set; }
        public bool PlayWithBull { get; set; }
        public HitTarget HittedTarget { get; set; }

        public int CalculateNextNumber(int currHitNo)
        {
            return 0;
        }
    }
    
    class RandomFast : IXATCStrategy
    {
        private List<int> list = MyDictionary.XATCRandomNumbers;
        public ATCGameType GameType { get; set; }
        public ATCDirection Direction { get; set; }
        public ATCSpeed Speed { get; set; }
        public bool PlayWithBull { get; set; }
        public HitTarget HittedTarget { get; set; }

        public int CalculateNextNumber(int currHitNo)
        {
            return 0;
        }
    }


Und der Aufruf dann so:


 IXATCStrategy nextTargetToHitStrategy = new NextTargetToHitStrategy(_gameType, _atcDirection, _atcSpeed, _playWithBull, hittarget).GetStrategory();
int strategyResult = nextTargetToHitStrategy.CalculateNextNumber(currHitNo);
System.Diagnostics.Debug.WriteLine("Strategy Result: " + strategyResult);

Warnung von Abt vor 8 Jahren

Was müssen wir noch tun, damit Du nach fast 7 Jahren im Forum dann doch endlich auf Fullquotes verzichtest?
[Hinweis] Wie poste ich richtig? 2.3

3.003 Beiträge seit 2006
vor 8 Jahren

Im Prinzip - ja. Ich bin sicher, dass man etliche der Properties noch loswerden und das Interface so entschlacken kann.

LaTino

"Furlow, is it always about money?"
"Is there anything else? I mean, how much sex can you have?"
"Don't know. I haven't maxed out yet."
(Furlow & Crichton, Farscape)

elTorito Themenstarter:in
177 Beiträge seit 2009
vor 8 Jahren

Ja. Mal schauen was sich noch machen lässt.

Hilft auf jedenfall schonmal, ist der Code doch bisschen verständlicher geworden , zumindest klappt nun alles auf Anhieb wo ich die Tage am rummurksen war und den Überblick verloren hatte. 😁

Danke nochmal.