Directred Event Multicasting

Collapse
This topic is closed.
X
X
 
  • Time
  • Show
Clear All
new posts
  • Pete

    #1

    Directred Event Multicasting

    Assume I have an n by n matrix of identical objects, each of which can both
    invoke and consume event A. If, say, obect[1,2] invokes the event, the only
    other objects that need to consume it are those in row 1 and those in column
    2. Sending the notification to other objects would be a waste of CPU.

    Is there an "approved" / efficient way to cause only those objects in row 1
    and column 2 to receive the event notification? I've looked but just don't
    see (or don't recognize) such a thing in the documentation.. .

    Thanks in advance.
  • Jon Skeet [C# MVP]

    #2
    Re: Directred Event Multicasting

    Pete <pbb@nospam.nos pam> wrote:[color=blue]
    > Assume I have an n by n matrix of identical objects, each of which can both
    > invoke and consume event A. If, say, obect[1,2] invokes the event, the only
    > other objects that need to consume it are those in row 1 and those in column
    > 2. Sending the notification to other objects would be a waste of CPU.
    >
    > Is there an "approved" / efficient way to cause only those objects in row 1
    > and column 2 to receive the event notification? I've looked but just don't
    > see (or don't recognize) such a thing in the documentation.. .[/color]

    Does the object itself know its position and the objects in the other
    positions?

    I must say, it's not something I've encountered a need for before...

    --
    Jon Skeet - <skeet@pobox.co m>
    http://www.pobox.com/~skeet Blog: http://www.msmvps.com/jon.skeet
    If replying to the group, please do not mail me too

    Comment

    • Kevin Yu [MSFT]

      #3
      Re: Directred Event Multicasting

      Hi,

      If this event is only handled by certain object, you only need to add the
      delegate to the event handler of the single object.

      Kevin Yu
      =======
      "This posting is provided "AS IS" with no warranties, and confers no
      rights."

      Comment

      • Pete

        #4
        Re: Directred Event Multicasting

        Sorry for the top posting.

        If necessary, the objects can be made aware of their own position in the
        matrix and can be told about other objects and their locations (all of which
        are fixed). It would be better, though, if each object could remain
        insensitive to context - to be able to fire the event and to have some
        higher level entity route that event as required.

        The problem I'm trying to solve is somewhat analogous to the Eight Queens
        problem in chess. If I place a rook on a particular square (i.e. a
        particular object becomes occupied), I'd like the other squares (objects) on
        that rank and file to know that they're under attack. The newly occupied
        square needn't care which other squares are under attack nor does the
        attacked square care from where the attack comes.

        In my case, I'm trying to build a Su Doku solver. In Su Doku, each square in
        the matrix can potentially have one of nine values (1 through 9) and once
        the value of a square is fixed, no other square on that rank or file can
        have the same value. The idea is that if the value of square[m, n] becomes
        fixed (e.g., it's known to be X), it would fire an event to be consumed by
        the other squares on that rank or file, telling them to remove X from their
        list of potential values. If that causes the value of the consuming cell to
        become fixed, the consuming cell would fire off it's own similar event to
        squares on it's rank and file.

        I understand there are plenty of ways to do this depth-first search. I just
        wondered if there was a way to use the event mechanism to get that for free.
        (And, also, because it would be kind-of interesting to try.)


        "Jon Skeet [C# MVP]" <skeet@pobox.co m> wrote in message
        news:MPG.1e1679 90539bc4e398cbb c@msnews.micros oft.com...[color=blue]
        > Pete <pbb@nospam.nos pam> wrote:[color=green]
        >> Assume I have an n by n matrix of identical objects, each of which can
        >> both
        >> invoke and consume event A. If, say, obect[1,2] invokes the event, the
        >> only
        >> other objects that need to consume it are those in row 1 and those in
        >> column
        >> 2. Sending the notification to other objects would be a waste of CPU.
        >>
        >> Is there an "approved" / efficient way to cause only those objects in row
        >> 1
        >> and column 2 to receive the event notification? I've looked but just
        >> don't
        >> see (or don't recognize) such a thing in the documentation.. .[/color]
        >
        > Does the object itself know its position and the objects in the other
        > positions?
        >
        > I must say, it's not something I've encountered a need for before...
        >
        > --
        > Jon Skeet - <skeet@pobox.co m>
        > http://www.pobox.com/~skeet Blog: http://www.msmvps.com/jon.skeet
        > If replying to the group, please do not mail me too[/color]


        Comment

        • Pete

          #5
          Re: Directred Event Multicasting


          "Jon Skeet [C# MVP]" <skeet@pobox.co m> wrote in message
          news:MPG.1e1679 90539bc4e398cbb c@msnews.micros oft.com...[color=blue]
          > Pete <pbb@nospam.nos pam> wrote:[color=green]
          >> Assume I have an n by n matrix of identical objects, each of which can
          >> both
          >> invoke and consume event A. If, say, obect[1,2] invokes the event, the
          >> only
          >> other objects that need to consume it are those in row 1 and those in
          >> column
          >> 2. Sending the notification to other objects would be a waste of CPU.
          >>
          >> Is there an "approved" / efficient way to cause only those objects in row
          >> 1
          >> and column 2 to receive the event notification? I've looked but just
          >> don't
          >> see (or don't recognize) such a thing in the documentation.. .[/color]
          >
          > Does the object itself know its position and the objects in the other
          > positions?
          >
          > I must say, it's not something I've encountered a need for before...
          >
          > --
          > Jon Skeet - <skeet@pobox.co m>
          > http://www.pobox.com/~skeet Blog: http://www.msmvps.com/jon.skeet
          > If replying to the group, please do not mail me too[/color]

          I suppose I could restate the problem for greater clarity.

          Assume I have a form with two buttons, exactly one of which should be
          enabled at any instant. The traditional way would be to have the form
          consume the Clicked event for both buttons and to have the event handler for
          each button set the Enabled property of the other button to False. I'm sure,
          also, that one could set things up so that the two buttons could mutually
          consume each others Clicked events, taking the form out of the mix
          altogether.

          But both of those approaches get a bit tedious when one introduces 81
          buttons and each button has a different set of event trading partners. It
          would be way cool if it were possible for, say, a single event handler to
          trap the Clicked events for all buttons and, then, re-route those events (as
          events, unchanged) by simply iterating over some data structure that
          captures the inter-relationships between buttons.

          It would be something like having a generic event (i.e., "some button,
          somewhere has been clicked") but, then, only the buttons that need to know -
          based on some higher-level(perhaps dynamically changing) criteria - would be
          notified of that event.


          Comment

          • Jon Skeet [C# MVP]

            #6
            Re: Directred Event Multicasting

            Pete <pbb@nospam.nos pam> wrote:[color=blue]
            > Sorry for the top posting.[/color]

            No problem - although I must say I'm intrigued as to why you apologised
            rather than not top posting :)
            [color=blue]
            > If necessary, the objects can be made aware of their own position in the
            > matrix and can be told about other objects and their locations (all of which
            > are fixed). It would be better, though, if each object could remain
            > insensitive to context - to be able to fire the event and to have some
            > higher level entity route that event as required.[/color]

            Well, here's an alternative way - make each of the squares expose an
            event, and make each square subscribe to the events it's interested in.
            So each square on the top row would subscribe to the "changed" event of
            each of the other squares on the top row, etc.

            The "routing" would be done once, at startup - and then you'd just fire
            the event. That's the only way I can see of doing it without the square
            being aware of its own position. (There may be ways I can't see, of
            course :)

            --
            Jon Skeet - <skeet@pobox.co m>
            http://www.pobox.com/~skeet Blog: http://www.msmvps.com/jon.skeet
            If replying to the group, please do not mail me too

            Comment

            • Jon Skeet [C# MVP]

              #7
              Re: Directred Event Multicasting

              Pete <pbb@nospam.nos pam> wrote:[color=blue]
              > I suppose I could restate the problem for greater clarity.
              >
              > Assume I have a form with two buttons, exactly one of which should be
              > enabled at any instant. The traditional way would be to have the form
              > consume the Clicked event for both buttons and to have the event handler for
              > each button set the Enabled property of the other button to False. I'm sure,
              > also, that one could set things up so that the two buttons could mutually
              > consume each others Clicked events, taking the form out of the mix
              > altogether.
              >
              > But both of those approaches get a bit tedious when one introduces 81
              > buttons and each button has a different set of event trading partners.[/color]

              Surely it only gets tedious when you need to wire up the events
              manually. There's no need for that. For instance, you could have code
              like this:
              using System;

              public class Square
              {
              const int GridSize = 9;

              public event EventHandler Changed;

              public static void Main()
              {
              // Create all the squares
              Square[,] grid = new Square[GridSize,GridSi ze];

              for (int i=0; i < GridSize; i++)
              {
              for (int j=0; j < GridSize; j++)
              {
              grid[i,j] = new Square();
              }
              }

              // Wire up all the events
              for (int i=0; i < GridSize; i++)
              {
              for (int j=0; j < GridSize; j++)
              {
              // Other squares in the same row and column
              // should subscribe
              for (int k=0; k < GridSize; k++)
              {
              if (k != i)
              {
              grid[i,j].Changed += new EventHandler
              (grid[k,j].ChangeHandler) ;
              }
              if (k != j)
              {
              grid[i,j].Changed += new EventHandler
              (grid[i,k].ChangeHandler) ;
              }
              }
              }
              }
              }

              public void ChangeHandler(o bject sender, EventArgs e)
              {
              // Do stuff here
              }
              }
              [color=blue]
              > It would be way cool if it were possible for, say, a single event handler to
              > trap the Clicked events for all buttons and, then, re-route those events (as
              > events, unchanged) by simply iterating over some data structure that
              > captures the inter-relationships between buttons.[/color]

              It would have to know which location had changed though. Either the
              square has to know, and tell the event handler that it was that square
              (which it would normally do with the "sender" argument), or the event
              handler would need to look it up to find the right square.
              [color=blue]
              > It would be something like having a generic event (i.e., "some button,
              > somewhere has been clicked") but, then, only the buttons that need to know -
              > based on some higher-level(perhaps dynamically changing) criteria - would be
              > notified of that event.[/color]

              As I say though, you still need the knowledge of what's been clicked
              *somewhere*.

              --
              Jon Skeet - <skeet@pobox.co m>
              http://www.pobox.com/~skeet Blog: http://www.msmvps.com/jon.skeet
              If replying to the group, please do not mail me too

              Comment

              • Pete

                #8
                Re: Directred Event Multicasting


                "Jon Skeet [C# MVP]" <skeet@pobox.co m> wrote in message
                news:MPG.1e1761 edbad690998cbd0 @msnews.microso ft.com...[color=blue]
                > Pete <pbb@nospam.nos pam> wrote:[color=green]
                >> I suppose I could restate the problem for greater clarity.
                >>
                >> Assume I have a form with two buttons, exactly one of which should be
                >> enabled at any instant. The traditional way would be to have the form
                >> consume the Clicked event for both buttons and to have the event handler
                >> for
                >> each button set the Enabled property of the other button to False. I'm
                >> sure,
                >> also, that one could set things up so that the two buttons could mutually
                >> consume each others Clicked events, taking the form out of the mix
                >> altogether.
                >>
                >> But both of those approaches get a bit tedious when one introduces 81
                >> buttons and each button has a different set of event trading partners.[/color]
                >
                > Surely it only gets tedious when you need to wire up the events
                > manually. There's no need for that. For instance, you could have code
                > like this:
                > using System;
                >
                > public class Square
                > {
                > const int GridSize = 9;
                >
                > public event EventHandler Changed;
                >
                > public static void Main()
                > {
                > // Create all the squares
                > Square[,] grid = new Square[GridSize,GridSi ze];
                >
                > for (int i=0; i < GridSize; i++)
                > {
                > for (int j=0; j < GridSize; j++)
                > {
                > grid[i,j] = new Square();
                > }
                > }
                >
                > // Wire up all the events
                > for (int i=0; i < GridSize; i++)
                > {
                > for (int j=0; j < GridSize; j++)
                > {
                > // Other squares in the same row and column
                > // should subscribe
                > for (int k=0; k < GridSize; k++)
                > {
                > if (k != i)
                > {
                > grid[i,j].Changed += new EventHandler
                > (grid[k,j].ChangeHandler) ;
                > }
                > if (k != j)
                > {
                > grid[i,j].Changed += new EventHandler
                > (grid[i,k].ChangeHandler) ;
                > }
                > }
                > }
                > }
                > }
                >
                > public void ChangeHandler(o bject sender, EventArgs e)
                > {
                > // Do stuff here
                > }
                > }
                >[color=green]
                >> It would be way cool if it were possible for, say, a single event handler
                >> to
                >> trap the Clicked events for all buttons and, then, re-route those events
                >> (as
                >> events, unchanged) by simply iterating over some data structure that
                >> captures the inter-relationships between buttons.[/color]
                >
                > It would have to know which location had changed though. Either the
                > square has to know, and tell the event handler that it was that square
                > (which it would normally do with the "sender" argument), or the event
                > handler would need to look it up to find the right square.
                >[color=green]
                >> It would be something like having a generic event (i.e., "some button,
                >> somewhere has been clicked") but, then, only the buttons that need to
                >> know -
                >> based on some higher-level(perhaps dynamically changing) criteria - would
                >> be
                >> notified of that event.[/color]
                >
                > As I say though, you still need the knowledge of what's been clicked
                > *somewhere*.
                >
                > --
                > Jon Skeet - <skeet@pobox.co m>
                > http://www.pobox.com/~skeet Blog: http://www.msmvps.com/jon.skeet
                > If replying to the group, please do not mail me too[/color]

                Yeah! You're right on all points. I suppose I was just thinking it might be
                nice to have, in addition to the (sender, eventArgs) semantics, something
                along the lines of (receiver, eventArgs) and/or (sender, receiver,
                eventArgs) semantics also available. Might not be handy all the time and it
                can be simutated by attaching and detaching event handlers but, well, you
                know...

                Thanks. Happy Holidays.


                Comment

                • Jon Skeet [C# MVP]

                  #9
                  Re: Directred Event Multicasting

                  Pete <pbb@nospam.nos pam> wrote:[color=blue]
                  > Yeah! You're right on all points. I suppose I was just thinking it might be
                  > nice to have, in addition to the (sender, eventArgs) semantics, something
                  > along the lines of (receiver, eventArgs) and/or (sender, receiver,
                  > eventArgs) semantics also available. Might not be handy all the time and it
                  > can be simutated by attaching and detaching event handlers but, well, you
                  > know...[/color]

                  Hmm. One of the nice things about the current eventing model is that
                  the object raising the event doesn't need to know *anything* about
                  what's handling it - just that there's a delegate of the right type for
                  it to invoke. I think when you start specifying receivers, you lose a
                  lot of that elegance.

                  Of course, you can create any delegate you want and use it for your
                  event type - in your case you could create your own delegate which
                  included the position within the grid of the sender.
                  [color=blue]
                  > Thanks. Happy Holidays.[/color]

                  You too.

                  --
                  Jon Skeet - <skeet@pobox.co m>
                  http://www.pobox.com/~skeet Blog: http://www.msmvps.com/jon.skeet
                  If replying to the group, please do not mail me too

                  Comment

                  Working...