KNOWLEDGE BASE
Log In    |    Knowledge Base    |    4D Home
Tech Tip: A utility for Sorting an Object Array
PRODUCT: 4D | VERSION: 14.1 | PLATFORM: Mac & Win
Published On: June 5, 2014

As with Pointer and Picture arrays, the 4D command SORT ARRAY does not sort arrays declared with the command ARRAY OBJECT. The utility method below will sort an object array based on a given property name.

The code below is example use of the utility method.

ARRAY OBJECT($Object_Array;3)
OB SET($Object_Array{1};"value";"B")
OB SET($Object_Array{2};"value";"C")
OB SET($Object_Array{3};"value";"A")

SORT_OBJECT_ARRAY (->$Object_Array;"value";True)
SORT_OBJECT_ARRAY (->$Object_Array;"value";False)



If (True)
   If (False)
       Begin SQL
       /*
         Name: SORT_OBJECT_ARRAY
         Path: SORT_OBJECT_ARRAY

         Purpose: Simple Bubble Sort for an array object

         $1 - Pointer - Pointer to the object array
         $2 - Text - Property name to sort on
         $3 - Boolean - Direction: True< = Ascending, False = Decending
       */
       End SQL
   End if
   C_TEXT($MethodName_T)
   $MethodName_T:=Current method name
     //===================== Declare Variables ==================================
     //method_parameters_declarations
   C_POINTER($ObjArray_P;$1)
   C_TEXT($PropertyName_T;$2)
   C_BOOLEAN($Ascending_B;$3)
     //-----------------------------------------------------------------------
     //method_wide_constants_declarations
     //-----------------------------------------------------------------------
     //local_variable_declarations
   C_LONGINT($Ndx;$Jdx;$SOA;$RIS;$Params_L;$Type_L)
   C_OBJECT($Tmp_O)
   C_POINTER($Val_1_P;$Val_2_P)
   C_TEXT($Val_1_T;$Val_2_T)
   C_BOOLEAN($Val_1_B;$Val_2_B)
   C_REAL($Val_1_R;$Val_2_R)
   C_DATE($Val_1_D;$Val_2_D)
   C_TIME($Val_1_H;$Val_2_H)
End if

  //====================== Initialize and Setup ================================

$Params_L:=Count parameters
If (Asserted($Params_L=3;"Bad param count! Should have been 3, was "+String($Params_L)))

   $ObjArray_P:=$1
   $PropertyName_T:=$2
   $Ascending_B:=$3  // False = Decending

   If (Type($ObjArray_P->)=Object array)

     $SOA:=Size of array($ObjArray_P->)
     If ($SOA>0)

       $Type_L:=OB Get type($ObjArray_P->{1};$PropertyName_T)
       Case of
       : (($Type_L=Is text) | ($Type_L=Is string var))
         $Val_1_P:=(->$Val_1_T)
         $Val_2_P:=(->$Val_2_T)

       : (($Type_L=Is integer) | ($Type_L=Is longInt) | ($Type_L=Is real) | ($Type_L=Is float))
         $Val_1_P:=(->$Val_1_R)
         $Val_2_P:=(->$Val_2_R)

       : ($Type_L=Is boolean)
         $Val_1_P:=(->$Val_1_B)
         $Val_2_P:=(->$Val_2_B)

       : ($Type_L=Is date)
         $Val_1_P:=(->$Val_1_D)
         $Val_2_P:=(->$Val_2_D)

       : ($Type_L=Is time)
         $Val_1_P:=(->$Val_1_H)
         $Val_2_P:=(->$Val_2_H)

      Else
         $Type_L:=-1

       End case

         //=================== Method Actions =============================

       If ($Type_L#-1)
         If ($Ascending_B)
             // Sort Asending
           For ($Ndx;1;$SOA)
             For ($Jdx;1;$SOA-$Ndx)

               $Val_1_P->:=OB Get($ObjArray_P->{$Jdx};$PropertyName_T)
               $Val_2_P->:=OB Get($ObjArray_P->{$Jdx+1};$PropertyName_T)

               If ($Val_2_P-><$Val_1_P->)  // Ascending sort

                 $Tmp_O:=OB Copy($ObjArray_P->{$Jdx})
                 $ObjArray_P->{$Jdx}:=OB Copy($ObjArray_P->{$Jdx+1})
                 $ObjArray_P->{$Jdx+1}:=OB Copy($Tmp_O)

               End if

             End for
           End for

        Else
             // Sort Decending
           For ($Ndx;1;$SOA)
             For ($Jdx;1;$SOA-$Ndx)

               $Val_1_P->:=OB Get($ObjArray_P->{$Jdx};$PropertyName_T)
               $Val_2_P->:=OB Get($ObjArray_P->{$Jdx+1};$PropertyName_T)

               If ($Val_2_P->>$Val_1_P->)  // Decending sort

                 $Tmp_O:=OB Copy($ObjArray_P->{$Jdx})
                 $ObjArray_P->{$Jdx}:=OB Copy($ObjArray_P->{$Jdx+1})
                 $ObjArray_P->{$Jdx+1}:=OB Copy($Tmp_O)

               End if

             End for
           End for

         End if
       End if
     End if
   End if

     //======================== Clean up and Exit =================================

End if