Android Question Dependent Dim Declaration

DawningTruth

Active Member
Licensed User
I have a scenario where I need to Dim a variable to 2 different classes dependent on an option. When I do this, it gives an error saying that myItem is already declared when option = 2. It should not do this as option 1 is never executed. There is clearly a gap in my understanding. Any suggestions?

B4X:
If option = 1 Then
        Dim myItem As Class1
Else if option = 2 Then
        Dim myItem As Class2
End If
 

Erel

B4X founder
Staff member
Licensed User
Longtime User
You can create a factory method:
B4X:
Sub CreateObject(Option As Int) As Object
 Select Option
  Case 1
   Dim square1 As Square
   square1.Initialize(20)
   Return square1
 Case 2
  Dim rectangle1 As Rectangle
  rectangle1.Initialize(20, 40)
  Return rectangle1
 End Select
End Sub

'usage
Dim shape As Object = CreateObject(option)
CallSub(shape, "draw")
 
Upvote 0

DawningTruth

Active Member
Licensed User
You can create a factory method:
B4X:
Sub CreateObject(Option As Int) As Object
 Select Option
  Case 1
   Dim square1 As Square
   square1.Initialize(20)
   Return square1
 Case 2
  Dim rectangle1 As Rectangle
  rectangle1.Initialize(20, 40)
  Return rectangle1
 End Select
End Sub

'usage
Dim shape As Object = CreateObject(option)
CallSub(shape, "draw")
Thx Erel, I will see how my sub can be adapted to this approach.
 
Upvote 0

advansis

Active Member
Licensed User
Longtime User
Why not declare the variable as object and let the called-function to choose the right behaviour? In this case you will use the select-case statement, after the calling and not before (as Erel suggests). The magic word to distinguish between classes is "is"
 
Upvote 0

MarkusR

Well-Known Member
Licensed User
Longtime User
...and let the called-function to choose the right behaviour? In this case you will use the select-case statement, after the calling and not before (as Erel suggests).
that i meant with a third class, as object u not see the methods.
 
Upvote 0

DawningTruth

Active Member
Licensed User
Why not declare the variable as object and let the called-function to choose the right behaviour? In this case you will use the select-case statement, after the calling and not before (as Erel suggests). The magic word to distinguish between classes is "is"
Advansis, please share a code stub, so I can understand what you mean. My current approach was to pass the object to the Sub, and then use it in what ever form is required in the sub. But that is not working for the reason above.
 
Upvote 0

advansis

Active Member
Licensed User
Longtime User
The skeleton could be this...

First approach: each class is independent
B4X:
Sub CreateObject (option As Int)
    Dim X As Object
   If option = 1 Then
       Dim M1 As Class1
       M1.initialize
       X=M1
   Else if option = 2 Then
       Dim M2 As Class2
       M2.initialize
       X=M2
   Else
       Return
   End If
   UseTheObject(X)
End Sub


' The dispatcher

Sub UseTheObject (X As Object)
   If X Is Class1 Then
       Dim M1 As Class1
       M1=X          
       ' Use of M1
   else if X Is Class2 Then
       Dim M2 As Class1
       M2=X
       ' Use of M2
   Else
       Return
   End If
End Sub

Second approach: using something like polimorphism:

B4X:
' The object creation

Sub CreateObject (option As Int)
    Dim X As Object
    If option = 1 Then
        Dim M1 As Class1
        M1.initialize
        X=M1
    Else if option = 2 Then
        Dim M2 As Class2
        M2.initialize
        X=M2
    Else
        Return
    End If
   
    UseTheObject(X)      
End Sub


' The dispatcher

Sub UseTheObject (X As Object)
    ' Calling some class methods...
    If SubExists(X,"Foo1") Then CallSub(X,"Foo1")
    If SubExists(X,"Foo2") Then CallSub2(X,"Foo2","xyz")
    If SubExists(X,"Foo3") Then CallSub3(X,"Foo3","abc","123")

    ' Calling with multiple parameters
    Dim Args As Map=CreateMap("Param1":1,"Param2","xyz","Param3","abc123")
    If SubExists(X,"FooM") Then CallSub2(X,"FooM",Args)
    Dim FooRes As String=Args.GetDefault("RetParam","")
       
End Sub
 
Upvote 0

DawningTruth

Active Member
Licensed User
The skeleton could be this...

First approach: each class is independent
B4X:
Sub CreateObject (option As Int)
    Dim X As Object
   If option = 1 Then
       Dim M1 As Class1
       M1.initialize
       X=M1
   Else if option = 2 Then
       Dim M2 As Class2
       M2.initialize
       X=M2
   Else
       Return
   End If
   UseTheObject(X)
End Sub


' The dispatcher

Sub UseTheObject (X As Object)
   If X Is Class1 Then
       Dim M1 As Class1
       M1=X         
       ' Use of M1
   else if X Is Class2 Then
       Dim M2 As Class1
       M2=X
       ' Use of M2
   Else
       Return
   End If
End Sub

Second approach: using something like polimorphism:

B4X:
' The object creation

Sub CreateObject (option As Int)
    Dim X As Object
    If option = 1 Then
        Dim M1 As Class1
        M1.initialize
        X=M1
    Else if option = 2 Then
        Dim M2 As Class2
        M2.initialize
        X=M2
    Else
        Return
    End If
  
    UseTheObject(X)     
End Sub


' The dispatcher

Sub UseTheObject (X As Object)
    ' Calling some class methods...
    If SubExists(X,"Foo1") Then CallSub(X,"Foo1")
    If SubExists(X,"Foo2") Then CallSub2(X,"Foo2","xyz")
    If SubExists(X,"Foo3") Then CallSub3(X,"Foo3","abc","123")

    ' Calling with multiple parameters
    Dim Args As Map=CreateMap("Param1":1,"Param2","xyz","Param3","abc123")
    If SubExists(X,"FooM") Then CallSub2(X,"FooM",Args)
    Dim FooRes As String=Args.GetDefault("RetParam","")
      
End Sub

Thx, I will study in more depth.
 
Upvote 0
Top