Indirekter Function-Aufruf über einen Delegaten

Deutschsprachiges X#-Forum – German language forum

Moderator: wriedmann

User avatar
pemo18
Posts: 72
Joined: Fri Apr 27, 2018 10:38 am
Location: Germany

Indirekter Function-Aufruf über einen Delegaten

Post by pemo18 »

Hallo Zusammen,

Ich würde gerne eine Art "Funktionsaufruftabelle" implementieren, damit ich Functions über ein Dictionary und einen Schlüssel indirekt aufrufen kann. In C# gibt es dafür Delegaten und die Invoke()-Methode.

In X# habe ich es leider noch nicht geschafft, da ich noch kein Pendant zur Invoke()-Methode gefunden habe.

Hier ist mein kleines Beispiel:

Code: Select all

 
   Delegate funDel() As String
    
    FUNCTION f1 As string
        return "Bewölkt"
   
    FUNCTION f2 As string
        return "Sonne"
   
    FUNCTION f3 As string
        return "Regen"

    FUNCTION Start() AS VOID STRICT
        Local funDic AS Dictionary<int, delegate>
        Local f1del As funDel
        Local f2del As funDel
        Local f3del As funDel
        f1Del := funDel{f1}    
        f2Del := funDel{f2}    
        f3Del := funDel{f3}    
        funDic := Dictionary<int, delegate>{}
        funDic:Add(1, f1del)
        funDic:Add(2, f2del)
        funDic:Add(3, f3del)
        Local z as int
        Local rnd As Random 
        rnd := Random{}
        z := 1
        Local vorhersage as Delegate
        vorhersage := funDic[z]
        Local wetter as string
        wetter := vorhersage
        Console.WriteLine("Die Wettervorhersage für heute: {0}", vorhersage)
        Console.ReadKey()
Meine Frage ist: Wie ich kann ich eine Function über einen Delegaten ausführen?

In der Doku bzw. dem Helpfile habe ich dazu nichts gefunden.

Danke schon einmal im Voraus für einen Tipp und viele Grüße,
Peter
User avatar
robert
Posts: 4225
Joined: Fri Aug 21, 2015 10:57 am
Location: Netherlands

Indirekter Function-Aufruf über einen Delegaten

Post by robert »

Peter,

Did you look at: https://www.xsharp.eu/help/lamda-expressions.html
it shows how to call delegates.
Of course in this example the delegates are Lambda expressions, but they can also be the name of a method.
Or try this:

DELEGATE Max(n1 AS INT, n2 AS INT) AS INT
FUNCTION Start AS VOID
LOCAL delMax AS Max
delMax := CalcMax
? delMax (1,2)
? delMax(4,3)
wait
RETURN

FUNCTION CalcMax(n1 AS INT, n2 AS INT) AS INT
IF n1 > n2
RETURN n1
ELSE
RETURN n2
ENDIF
XSharp Development Team
The Netherlands
robert@xsharp.eu
User avatar
pemo18
Posts: 72
Joined: Fri Apr 27, 2018 10:38 am
Location: Germany

Indirekter Function-Aufruf über einen Delegaten

Post by pemo18 »

Hello Robert,

Thank you very much. That looks like the missing piece I was looking for.

Kind regards,
Petr
User avatar
pemo18
Posts: 72
Joined: Fri Apr 27, 2018 10:38 am
Location: Germany

Indirekter Function-Aufruf über einen Delegaten

Post by pemo18 »

This is the working example that also proves how elegant the X# syntax is:

Code: Select all

Delegate funDel() As String
    
FUNCTION Start() As VOID STRICT
        Local funDic := Dictionary<int, fundel>{} As Dictionary<int, fundel>
        Local f1del := { => "Etwas bewölkter" } As funDel 
        Local f2del := { => "Immer sonniger" } As funDel
        Local f3del := { => "Deutlich regnerischer" } As funDel
        funDic:Add(1, f1del)
        funDic:Add(2, f2del)
        funDic:Add(3, f3del)
        Local z := Random{}:@@Next(1,funDic:Count + 1) As Int
        Console.WriteLine("Die Wettervorhersage für heute: {0}", funDic[z]())
        Console.ReadKey()
Kind regads,
Peter
User avatar
lumberjack
Posts: 723
Joined: Fri Sep 25, 2015 3:11 pm

Indirekter Function-Aufruf über einen Delegaten

Post by lumberjack »

Hi,

Try:

Code: Select all

 
   Delegate funDel() As String
    
    FUNCTION f1 As string
        return "Bewölkt"
   
    FUNCTION f2 As string
        return "Sonne"
   
    FUNCTION f3 As string
        return "Regen"

    FUNCTION Start() AS VOID STRICT
        Local funDic AS Dictionary<int, funDel>
        Local f1del As funDel
        Local f2del As funDel
        Local f3del As funDel
        f1Del := funDel{null, @f1()}    
        f2Del := funDel{null, @f2()}    
        f3Del := funDel{null, @f3()}    
        funDic := Dictionary<int, funDel>{}
        funDic:Add(1, f1del)
        funDic:Add(2, f2del)
        funDic:Add(3, f3del)
        Local z as int
        Local rnd As Random 
        rnd := Random{}
        z := 1
        Local vorhersage as funDel
        vorhersage := funDic[z]
        Local wetter as string
        wetter := vorhersage()
        Console.WriteLine("Die Wettervorhersage für heute: {0}", vorhersage)
        Console.ReadKey()
Hope this helps, good luck!
User avatar
lumberjack
Posts: 723
Joined: Fri Sep 25, 2015 3:11 pm

Indirekter Function-Aufruf über einen Delegaten

Post by lumberjack »

Robert,
robert wrote:Peter,
Or try this:
You beat me by a split second. Obviously I have tried to modify his code the VN way... Not sure if that still work?
Regards,
FFF
Posts: 1522
Joined: Fri Sep 25, 2015 4:52 pm
Location: Germany

Indirekter Function-Aufruf über einen Delegaten

Post by FFF »

Both of you need a
USING system.Collections.Generic at the top, then Robert's works, while Johan's version returns "funDel" instead :)
Regards
Karl
(on Win8.1/64, Xide32 2.19, X#2.19.0.2.)
User avatar
robert
Posts: 4225
Joined: Fri Aug 21, 2015 10:57 am
Location: Netherlands

Indirekter Function-Aufruf über einen Delegaten

Post by robert »

Johan,

In stead of

Code: Select all

f1Del := funDel{null, @f1()}

you can also use

Code: Select all

f1Del := f1
You were indeed using the VN syntax

Robert
XSharp Development Team
The Netherlands
robert@xsharp.eu
User avatar
lumberjack
Posts: 723
Joined: Fri Sep 25, 2015 3:11 pm

Indirekter Function-Aufruf über einen Delegaten

Post by lumberjack »

Hi Karl,
FFF wrote:Both of you need a
USING system.Collections.Generic at the top, then Robert's works, while Johan's version returns "funDel" instead :)
I will however need to install System.Collections.Languages.German additionally...
User avatar
pemo18
Posts: 72
Joined: Fri Apr 27, 2018 10:38 am
Location: Germany

Indirekter Function-Aufruf über einen Delegaten

Post by pemo18 »

Thank you everyone.

This is the shortest (and still readable) version I came up with:

Code: Select all

USING System
USING System.Collections.Generic

BEGIN NAMESPACE IndirekterAufruf

Delegate funDel() As String
    
FUNCTION Start() AS VOID STRICT
        Local funDic := Dictionary<int, fundel>{} AS Dictionary<int, fundel>
        funDic:Add(1, { => "Cloudy day ahead" }  )
        funDic:Add(2, { => "Sunny the whole day" })
        funDic:Add(3, { => "Rain, rain and even more rain" })
        Local z := Random{}:@@Next(1,funDic:Count + 1) as int
        Console.WriteLine("The weather forecast for today: {0}", funDic[z]())
If XSharp is as close to C# as I assume I probably don't have to use a delegate.

I even found a translation class;)

Peter
Post Reply