About Monkey 2 › Forums › Monkey 2 Programming Help › sort with list
This topic contains 7 replies, has 4 voices, and was last updated by 
 medi
 2 years, 1 month ago.
- 
		AuthorPosts
 - 
		
			
				
March 15, 2017 at 7:20 pm #7502
I have used ‘Compare’ below to sort a linked list in BlitzMax:
Monkey1234567891011121314151617181920Type MyTypeField a:intField b:intField c:intField d:int...Method Compare:Int(otherObject:Object)Local t:MyType= MyType(otherObject)If Not tReturn 1EndIfReturn a - t.a ..Or b - t.b ..Or c - t.c ..End MethodEnd TypeHow to do this in Monkey 2?
March 15, 2017 at 7:36 pm #7503Hi
to place source code use the button ‘crayon’ in the text-box, it will open a proper ‘code editor’ where you can paste the source.
About list and ‘compare’ method follow this example
http://monkey2.monkey-x.com/forums/topic/a-clever-way-to-filter-lists/
March 15, 2017 at 8:03 pm #7504Thanks for the help!
How about this:
Monkey1Method Sort:Void( compareFunc:Int( T,T ) )in the manual, rather than a kind of IComapre? Will play with that for a while, then I will go back to the link.
March 16, 2017 at 12:53 am #7505Here’s the basic idea:
Monkey1234567891011121314151617181920212223#Import "<std>"Using std..Function Main()Local stack:=New Stack<Float>( 10 )For Local i:=0 Until stack.Lengthstack[i]=Rnd()Nextstack.Sort( Lambda:Int( x:Float,y:Float )Return x<=>yEnd )For Local t:=Eachin stackPrint tNextEndThe ‘lambda’ is an ‘inline’ funtion. You can also use a global function or method here, eg: stack.Sort( MyGlobalCompareFunc ).
The ‘<=>’ operator might look a bit weird, but it basically just returns an int value <0 if x<y, >0 if x>y and 0 if x=y. This is the default behavior if you just call Sort() with no comparison param.
March 16, 2017 at 1:19 am #7506Mark just beat me to it, about the ‘<=>’ operator. Anyway, here’s what I whipped up:
[/crayon]Monkey12345678910111213141516171819202122232425262728293031323334353637383940414243444546474849505152535455565758596061626364[crayon-5cba152d94e1b669676159 inline="true" ]#Import "<std>"Using std..Function Main()Local scores := New Stack<Score>()Local PrintAllScores := Lambda:Void(heading:String)Print heading + "~n"For Local score:= Eachin scoresPrint score.ToString()NextPrint "~n~n"Endscores.Push(New Score("Joe Blogs", 11))scores.Push(New Score("Iron Man", 23))scores.Push(New Score("Jane Doe", 12))scores.Push(New Score("Dudeson", 10))PrintAllScores("Before Sort")scores.Sort(False)PrintAllScores("After Sort")EndClass ScorePrivateField _name:StringField _value:IntPublicMethod New(name:String, value:Int)Name = nameValue = valueEndProperty Name:String()Return _nameSetter (name:String)_name = nameEndProperty Value:Int()Return _valueSetter (value:Int)_value = valueEndOperator<=>:Int(cmp:Score)Return Value<=>cmp.ValueEndMethod ToString:String()Return Name + "~t~t" + ValueEndEndMarch 16, 2017 at 4:26 am #7507Thanks, so back to my sort and making life easier, I got this:
Monkey12345678910111213141516171819202122232425262728293031323334353637383940414243444546474849505152535455565758596061626364656667686970717273747576777879808182838485868788899091#Import "<std>"Using std..Struct PersonField name:StringField age:StringField height:StringField weight:StringEndFunction ComparePersons:int(x:Person,y:Person)Return x.name<=>y.nameEnd FunctionFunction Main()Local per_list:= New List<Person>Local per:Person = New PersonPrint "---"per.name = "Aab"per.age = "45"per.height = "9"per.weight = "160"per_list.AddLast(per)per.name = "Elin"per.age = "45"per.height = "6"per.weight = "145"per_list.AddLast(per)per.name = "Sam"per.age = "75"per.height = "7"per.weight = "163"per_list.AddLast(per)per.name = "Aab"per.age = "45"per.height = "9"per.weight = "132"per_list.AddLast(per)per.name = "Sam"per.age = "45"per.height = "4"per.weight = "200"per_list.AddLast(per)per.name = "Elin"per.age = "15"per.height = "6"per.weight = "120"per_list.AddLast(per)per.name = "Aab"per.age = "15"per.height = "6"per.weight = "167"per_list.AddLast(per)per.name = "Sam"per.age = "75"per.height = "4"per.weight = "116"per_list.AddLast(per)For Local p := Eachin per_listPrint p.name + "," + p.age + "," + p.height + "," + p.weightNextLocal x:PersonLocal y:Personper_list.Sort(ComparePersons(x, y) )per_list.Sort(true)Print "--"For Local t:=Eachin per_listPrint t.name + "," + t.age + "," + t.height + "," + t.weightNextEndWhich prints:
Monkey12345678910111213141516171819---Aab,45,9,132Elin,45,6,145Sam,75,7,163Aab,45,9,160Sam,45,4,200Elin,15,6,120Aab,15,6,167Sam,75,4,116--Aab,15,6,167Aab,45,9,132Aab,45,9,160Elin,15,6,120Elin,45,6,145Sam,45,4,200Sam,75,4,116Sam,75,7,163Next stage?
a csvReader which I should figure out without readLine()
March 16, 2017 at 10:02 pm #7520…actually, this:
per_list.Sort(ComparePersons(x, y) )
looks a bit wrong. This actually calls the ‘ComparePersons’ function, but you probably wanted to pass the function to Sort() instead. The way to do that is simply:
per_list.Sort( ComparePersons )
Easy!
Since there is no ‘()’ after ComparePersons, the function is *not* actually called…
When you go:
per_list.Sort( ComparePersons(x,y) )
…this does actually call ComparePersons (which returns an int) and then passes the returned int as a parameter to Sort(), which is probably not what you meant.
Basically, ‘func()’ calls a function, while ‘func’ on its own does not. This takes a bit of getting used to but the main idea here is that it allows you to pass functions around just like they were ints or floats or arrays or strings or whatever!
March 17, 2017 at 1:17 am #7524Thanks Mark, at least I tried
 - 
		AuthorPosts
 
You must be logged in to reply to this topic.