Android Question [solved] Strang list problem

Discussion in 'Android Questions' started by JDS, Aug 7, 2019.

  1. JDS

    JDS Active Member Licensed User

    I've got a list defined in Starter Service Process_Globals (and yes it is initialized)

    Code:
    Sub Process_Globals
     
     
        
    Public arZendingen As List
    This list is filled with items of a type:
    Code:
    Type TZending (zendingid As String, _
            vrachtnr 
    As String, _
    Zendingregels 
    As List)
    I've made a copy of the arZendingen list to another list -> arZnd
    Now I want to add the Zendingregels of all items from arZnd to the first item of arZnd.

    The code below doesn't fail, it works however at the "<--MARK" -line happens something strange. Yes tRegel is added to tZend2.Zendingregels. But at the same moment the same item in com.arZendingen is updated also.

    Code:
    Dim tZend As TZending : tZend.initialize
        
    Dim tSort As TZending : tSort.initialize
        iSize = arZnd.Size-
    1
        
    Dim y As Int
        
    For i = 0 To iSize
            
    If i>iSize Then Exit
            
    If i=0 Then
                
    Dim tZend As TZending : tZend.Initialize
                tZend=arZnd.Get(i)
                y=i
            
    Else
                
    Dim tSort2 As TZending : tSort2.Initialize
                tSort2=arZnd.Get(i)
                
    If tSort2.customer<>tZend.customerThen
                    
    Dim tZend As TZending : tZend.Initialize
                    tZend=tSort
                    y=
    1
                
    Else
                    
    For j = 0 To tSort2.Zendingregels.Size-1
                        
    Dim tRegel As TRegel : tRegel.initialize
                        tRegel=tSort2.Zendingregels.Get(j)
                        tZend.Zendingregels.Add(tRegel) 
    '<--MARK
                            
                    
    Next
                    arZnd.RemoveAt(i)
                    arZnd.RemoveAt(y)
                    arZnd.InsertAt(y,tZend)
                    i=i-
    1
                    iSize=iSize-
    1
                
    End If
            
    End If
        
    Next
    Am I missing something? Any thoughts?
     
    Last edited: Aug 7, 2019
  2. DonManfred

    DonManfred Expert Licensed User

    Upload a small project which shows the issue.
     
  3. Erel

    Erel Administrator Staff Member Licensed User

    This is a mistake:
    Code:
    Dim tRegel As TRegel : tRegel.initialize
       tRegel=tSort2.Zendingregels.Get(j)
    There is no reason to initialize the object if you are assigning a different one to the same variable.

    Correct code:
    Code:
    Dim tRegel As TRegel = tSort2.Zendingregels.Get(j)
    "Copying" the objects from one list to another doesn't create a new copy of the objects. The lists only hold references to the objects and the references are copied.
     
    emexes likes this.
  4. emexes

    emexes Well-Known Member Licensed User

    I'm betting it is something to do with two object variables pointing to the same object.

    edit: Erel's explanation is probably better.

    I'm a bit doubtful about using a For loop that requires an additional loop variable test ie the loop limit is changing, and also where the loop variable is reversed/decremented inside the loop.

    Code like that usually works better as a while loop.

    Yes, you'll need an extra line of code to increment the loop variable, but at the same time, you'll save at least one line by not having the same loop test twice, and might even save another if you don't have to decrement it.
     
    Last edited: Aug 7, 2019
  5. JDS

    JDS Active Member Licensed User

    Code:
    #Region  Project Attributes
        
    #ApplicationLabel: B4A Example
        
    #VersionCode: 1
        
    #VersionName:
        
    'SupportedOrientations possible values: unspecified, landscape or portrait.
        #SupportedOrientations: unspecified
        
    #CanInstallToExternalStorage: False
    #End Region

    #Region  Activity Attributes
        
    #FullScreen: False
        
    #IncludeTitle: True
    #End Region

    Sub Process_Globals
        
    'These global variables will be declared once when the application starts.
        'These variables can be accessed from all modules.
        Dim arZendingen As List
    End Sub

    Sub Globals
        
    'These global variables will be redeclared each time the activity is created.
        'These variables can only be accessed from this module.
        Type TRegel (Eenheid As String, oms As String)
      
        
    Type TZending (zendingid As String, customer As Int, Zendingregels As List)
    End Sub

    Sub Activity_Create(FirstTime As Boolean)
        
    'Do not forget to load the layout file created with the visual designer. For example:
        'Activity.LoadLayout("Layout1")
      
        arZendingen.initialize
      
        
    For i = 0 To 9
            
    Dim tZnd As TZending : tZnd.initialize
            tZnd.zendingid=i+
    1000
            tZnd.Zendingregels.Initialize
            
    If i<4 Then
                tZnd.customer = 
    10
            
    Else
                tZnd.customer = 
    2
            
    End If
            
    For j = 0 To 4
                
    Dim tReg As TRegel : tReg.initialize
                tReg.Eenheid=
    "Eenheid "&j
                tReg.oms    =
    "Omschrijving "&(j+1000)
                tZnd.Zendingregels.Add(tReg)
            
    Next
            arZendingen.Add(tZnd)
        
    Next
      
      
    End Sub

    Sub Activity_Resume
      
        
    Dim iZnd As Int
        
    Dim tZend As TZending : tZend.initialize
        
    Dim llist As List : llist.initialize
        
    For i = 0 To arZendingen.Size-1
            tZend=arZendingen.Get(i)
            
    If tZend.customer < 10 Then
                llist.Add(tZend.zendingid)
            
    End If
          
        
    Next
      
        Createlist(llist)
      
    End Sub

    Sub Activity_Pause (UserClosed As Boolean)

    End Sub

    Sub Createlist(llist As List)
        
    Dim tZend As TZending : tZend.initialize
        
    Dim tSort As TZending : tSort.initialize
        
    Dim iZnd, iFound, iSize As Int
        
    Dim arZnd As List : arZnd.initialize
      
        
    For i = 0 To arZendingen.Size-1
            tZend=arZendingen.Get(i)
            
    For j = 0 To llist.Size-1
                iZnd=llist.Get(j)
                
    If iZnd=tZend.zendingid Then
                    
    If arZnd.Size=0 Then
                        arZnd.Add(tZend)
                    
    Else
                        iFound=
    0
                        
    For x = 0 To arZnd.Size-1
                            tSort=arZnd.Get(x)
                            
    If tSort.customer=tZend.customer Then
                                arZnd.InsertAt(x+
    1,tZend)
                                iFound=
    1
                                
    Exit
                            
    End If
                        
    Next
                        
    If (iFound=0Then arZnd.Add(tZend)
                    
    End If
                  
                    
    Exit
                
    End If
            
    Next
        
    Next
      
      
        
    Dim tZend As TZending : tZend.initialize
        
    Dim tSort As TZending : tSort.initialize
        iSize = arZnd.Size-
    1
        
    Dim y As Int
        
    For i = 0 To iSize
            
    If i>iSize Then Exit
            
    If i=0 Then
                
    Dim tZend As TZending : tZend.Initialize
                tZend=arZnd.Get(i)
                y=i
            
    Else
                
    Dim tSort2 As TZending : tSort2.Initialize
                tSort2=arZnd.Get(i)
                
    If tSort2.customer<>tZend.customer Then
                    
    Dim tZend As TZending : tZend.Initialize
                    tZend=tSort
                    y=
    1
                
    Else
                    
    For j = 0 To tSort2.Zendingregels.Size-1
                        
    Dim tRegel As TRegel =tSort2.Zendingregels.Get(j)
                        tZend.Zendingregels.Add(tRegel) 
    '<--MARK - in this example item 3 of arzendingen has 30 zendingregels but this should be 5
                      
                    
    Next
                    arZnd.RemoveAt(i)
                    arZnd.RemoveAt(y)
                    arZnd.InsertAt(y,tZend)
                    i=i-
    1
                    iSize=iSize-
    1
                
    End If
            
    End If
        
    Next
      
        
    Log("Done")
    End Sub
     
    Last edited: Aug 7, 2019
  6. JDS

    JDS Active Member Licensed User

    How can I create a copy a copy of a list? Without holding the references?
     
  7. JDS

    JDS Active Member Licensed User

    I've changed the example of post #5 with Erels suggestions but the problem persists.
     
  8. emexes

    emexes Well-Known Member Licensed User

    hang on, we have these three fields "zendingid", "vrachtnr", "Zendingregels" in the type:
    Code:
    Type TZending (zendingid As String, _
            vrachtnr 
    As String, _
    Zendingregels 
    As List)
    but then we have another field "Verlader" here:
    Code:
    Dim tSort2 As TZending : tSort2.Initialize
    tSort2=arZnd.Get(i)
    If tSort2.Verlader<>tZend.Verlader Then
    How does that work? Or is there some auto-translation happening that is mucking up words that aren't Dutch or English?
     
    Last edited: Aug 7, 2019
  9. DonManfred

    DonManfred Expert Licensed User

    Please use [CODE]code here...[/CODE] tags when posting code! You are member since 2012 and you should know that.
     
  10. JDS

    JDS Active Member Licensed User

    Done. Sorry, working too fast I guess...
     
  11. emexes

    emexes Well-Known Member Licensed User

    It looks like you want to sort the arZnd List by one of the subfields. Is this correct? If so, which subfield?
     
  12. JDS

    JDS Active Member Licensed User

    Changed. Originally it was "verlader" (=dutch) but changed it to "customer" for the English speaking users.
     
  13. JDS

    JDS Active Member Licensed User

    I want to merge al "Zendingregels" of one customer to one "Tzending". Futher on in the programm I'll create a PDF document where the "Zendingregels" are printed.
    This way I want to prevent looping al the items searching for the same customer when printing.
     
  14. Erel

    Erel Administrator Staff Member Licensed User

    My suggestion was not related to that problem.

    The problems happens because you are not making copies of the type.

    You can use this sub to make copies:
    Code:
    Sub DuplicateType (obj As Object) As Object
       
    Dim ser As B4XSerializator 'RandomAccessFile library
       Return ser.ConvertBytesToObject(ser.ConvertObjectToBytes(obj))
    End Sub
     
  15. JDS

    JDS Active Member Licensed User

    Fixed. Thanks Erel!
     
Loading...
  1. This site uses cookies to help personalise content, tailor your experience and to keep you logged in if you register.
    By continuing to use this site, you are consenting to our use of cookies.
    Dismiss Notice