Search Unity

  1. Megacity Metro Demo now available. Download now.
    Dismiss Notice
  2. Unity support for visionOS is now available. Learn more in our blog post.
    Dismiss Notice

sort int[]

Discussion in 'Scripting' started by fred_gds, Nov 27, 2012.

  1. fred_gds

    fred_gds

    Joined:
    Sep 20, 2012
    Posts:
    184
    Hey,

    Could anyone help me with my problem.

    I have this script made in js but it doesn't work and I don't see why it isn't;

    static var points : int[] = new int[5];
    var allPoints : int[] = new int[5];
    static var ranking : int[] = new int[5];

    function Update()
    {
    allPoints = points;
    System.Array.Sort(allPoints);
    for(var i : int = 0; i <= points.length; i++)
    {
    for(var b : int = 0; i <= allPoints.length; b++)
    {
    if(points == allPoints)
    {
    ranking = b;
    }
    }
    }
    }

    So I assign the ints for points in another script. And until allPoints = points; everything works fine. but in the following there is something that doesn't seem to work as I don't get any value for ranking. So I want ranking to return a value between 0-5 that should be the same as the b of allPoints above. And the i of ranking is supposed to stay the same as the i of points above.

    So it I'm sure that it isn't a small mistake as forgetting a ; or so (even if might have made such a mistake above :) )
     
  2. launchpad

    launchpad

    Joined:
    Aug 17, 2007
    Posts:
    95
    Is this what you are after?

    Code (csharp):
    1.  
    2. #pragma strict
    3.  
    4. import System;
    5.  
    6.  
    7. static var points : int[] =  [1,2,3,4,5];
    8. static var allPoints : int[] = [1,2,5];
    9. static var ranking : int[] = new int[5];
    10.  
    11.  
    12. function Start () {
    13.  
    14. Debug.Log("points: " + points.Length);
    15. Debug.Log("allPoints: " + allPoints.Length);
    16. //  allPoints = points;
    17. //  System.Array.Sort(allPoints);
    18.     for(var i = 0; i < points.length; i++)
    19.         {
    20.             for(var b = 0; b < allPoints.length; b++)
    21.                 {
    22.                    
    23.                    
    24.                     if(points[i] == allPoints[b])
    25.                     {
    26.                     Debug.Log("Show: " + points[i] + ", " + allPoints[b]);
    27.                    
    28.                             ranking[i] = b;
    29.                             Debug.Log("b: " + b);
    30.                     }
    31.                 }
    32.        
    33.  
    34.  
    35.         }
    36. }
    37.  
    Don't forget, arrays have a value zero therefore count comparisons should be less than array.Length
    Don't use Update for this, just a function call when required.
    You had a couple for other indexing issues etc.
    Regards, PW
     
  3. fred_gds

    fred_gds

    Joined:
    Sep 20, 2012
    Posts:
    184
    I don't think that thsi script is going to do it.

    So I'll try to explain what I want to do so if I have for example:

    object1 has 50 points
    object 2 has 60 points
    and object 3 has 55 points

    then the position of

    object1 would be 3
    object2 would be 1
    and object3 would be 2

    so I always have a number saved as int for each object and I have the number of points collected and I want to get the position in relation to the other objects.

    And I don't think that you are doing that in your script but please correct me if I'm wrong

    Thx anyways, Fred
     
  4. lordofduct

    lordofduct

    Joined:
    Oct 3, 2011
    Posts:
    8,514
    First and foremost, your biggest problem is that you're using 3 different arrays to relate shared data, meaning when one array gets sorted... all 3 arrays need to get sorted.

    Why not create a class or structure to represent this shared info?

    In C#

    Code (csharp):
    1.  
    2. public struct ObjectData
    3. {
    4.     public int points;
    5.     public int ranking;
    6.     public int allPoints;
    7. }
    8.  
    now each GameObject has an ObjectData associated with it

    now lets say you want to sort the array, you just sort the ONE array. This is pretty easy, mono/.net has a sort method built in.

    Code (csharp):
    1.  
    2. ObjectData[] arr = new ObjectData[5];
    3. //fill arr
    4.  
    5. Array.Sort(arr, delegate(ObjectData a, ObjectData b) {
    6.     if(a.points == b.points) return 0;
    7.     if(a.points > b.points) return 1;
    8.     else return -1;
    9. });
    10.  
     
  5. fred_gds

    fred_gds

    Joined:
    Sep 20, 2012
    Posts:
    184
    yeah thx

    I thought about that earlier but I didn't now how to do it.

    So your script looks good but could you maybe make it as js as I can't share variables in the different languages.
     
  6. lordofduct

    lordofduct

    Joined:
    Oct 3, 2011
    Posts:
    8,514
    what do you mean by "share variables in the different languages"?

    as for structs in unityscript

    you inherit from 'ValueType' to do it

    Code (csharp):
    1.  
    2. class ObjectData extends System.ValueType
    3. {
    4.     var points:int;
    5.     var ranking:int;
    6.     var allPoints:int;
    7. }
    8.  
    as for anonymous functions I believe you can say mid code:

    Code (csharp):
    1.  
    2. Array.Sort(arr, function(a,b) { //do stuff here });
    3.  
    other uses like
    Code (csharp):
    1.  
    2. var f:Function = function(a,b) { //do stuff };
    3. Array.Sort(arr, f);
    4.  
    and of course just explicitly like usual (which is valid in C# too)
    Code (csharp):
    1.  
    2. funciton foo(a:ObjectData, b:ObjectData)
    3. {
    4.      //do stuff
    5. }
    6.  
    7. function whereIDoTheSort()
    8. {
    9.     varr arr = *the array*;
    10.     Array.Sort(arr, foo);
    11. }
    12.  
     
    Last edited: Nov 28, 2012
  7. fred_gds

    fred_gds

    Joined:
    Sep 20, 2012
    Posts:
    184
    hmm so I imported the script to my project but I still have the Problem that I don't see how you use this :

    Array.Sort(arr, delegate(ObjectData a, ObjectData b) {

    if(a.points == b.points) return 0;

    if(a.points > b.points) return 1;

    else return -1;

    }); //is that right that you put the ) after the } ?

    to get the current ranking. could you maybe explain what exactly u are doing in those lines?
     
  8. lordofduct

    lordofduct

    Joined:
    Oct 3, 2011
    Posts:
    8,514
    first off, it's C#, so it'd have to be ported to unityscript if you are going to write it in that

    Array.Sort takes in an array and a function to use as the comparison algorithm. The Array.Sort will go through all the entries and compare them against each other to find out where they should be. To do this it calls the comparison function you pass in... in it you return 1 if a should be after b, -1 if it should be before, and 0 if it is the same.

    here is the MSDN article about it:
    http://msdn.microsoft.com/en-us/library/cxt053xf.aspx

    Now what I've created there in the code you repeated back to me is called an anonymous function in C#, I did it that way just because anonymous functions are inline and I don't have to define it elsewhere.

    Unityscript on the otherhand, being based on the ecma standard, treats functions as objects in and of themselves (where as C# uses delegates to reference functions). So creating anonymous anonymous functions in unityscript should be simpler... hence my second post where I showed you examples of anonymous functions in unityscript. In those examples I just put "//do stuff" where the code for said anonymous function should be... because I'm not going to rewrite said algorithm for each example I wrote above. All you have to do is inject the if/else statement in that spot... you should be able to handle that... if you can't, well you've got more important things to learn than sorting arrays.


    Note - I did NOT hand you copy pastable code. I handed you psuedo-code shaped like C#, and then more shaped like unityscript because you prefer unityscript. They are purely example code so you can learn. I do not give a man a fish, I teach a man to fish.
     
    Last edited: Nov 29, 2012
  9. fred_gds

    fred_gds

    Joined:
    Sep 20, 2012
    Posts:
    184
    sorry I'm not so good with array, I might just be too stupid :(

    so I wrote this:

    static var carsInformation : ObjectData[] = new ObjectData[5];

    class ObjectData extends System.ValueType
    {
    var points:int;
    var ranking:int;
    var allPoints:int;
    }
    function foo(a:ObjectData, b:ObjectData)
    {
    //do stuff
    }
    function Update()
    {
    carsInformation.points = carsInformation.allPoints;
    System.Array.Sort(carsInformation.allPoints, foo);
    }

    assigning carsInformation like this in another script

    var carsNumber : int;
    var pointsCollected :int;
    RankingScript.carsInformation[carsNumber].points = pointsCollected;

    but later on I only want to display smth like this:

    function OnGUI()
    {
    GUI.Label(new Rect(0,0,100,100),"Players Position: " + carsInformation[0].ranking)
    }


    but the script like this isn't making it :(
     
  10. lordofduct

    lordofduct

    Joined:
    Oct 3, 2011
    Posts:
    8,514
    first use the code blocks when posting code, it makes reading your code easier. The advanced reply screen has it built in if you can't remember it's
    Code (csharp):
    1. . Just click on the # symbol to inject the bbcode for it.
    2.  
    3.  
    4. So here you said you wrote:
    5.  
    6. [code]
    7. class ObjectData extends System.ValueType
    8. {
    9.     var points:int;
    10.     var ranking:int;
    11.     var allPoints:int;
    12. }
    13. function foo(a:ObjectData, b:ObjectData)
    14. {
    15.     //do stuff
    16. }
    17. function Update()
    18. {
    19.     carsInformation.points = carsInformation.allPoints;
    20.     System.Array.Sort(carsInformation.allPoints, foo);
    21. }
    22.  
    well you see this:

    Code (csharp):
    1.  
    2. function foo(a:ObjectData, b:ObjectData)
    3. {
    4.     //do stuff
    5. }
    6.  
    the //do stuff?

    That needs to be replaced with the actual comparison algorithm. Like the one I showed you before. That functions needs to return something... namely 1 if a is ahead of b, -1 if it's behind, and 0 if they're the same. This way Array.Sort knows in what order to put the elements of the array.