0

I have a method that I'd want to accept ref to a specific object:

    public static void Death(ref Animal unit)
{
...
}

And then i have :

object target

A generic object that can be a Animal and other stuff. If it's an Animal I want to cast target into Animal and then pass that ref to my Death method but I can't figure out how to do it...

user3161621
  • 75
  • 2
  • 8

2 Answers2

1
Animal a = target as Animal;
if(a != null)
{
    Death(ref a);
}

EDIT: If you want to modify target in Death, the only way is to do the check in there:

public static void Death(ref object unit)
{
    Animal a = unit as Animal;
    if(a != null)
    {
        //assign unit
    }
}
Lee
  • 142,018
  • 20
  • 234
  • 287
  • yes this syntax is correct but the effect doesnt work, i already tried it but the death method doesnt affect the real target – user3161621 Apr 19 '14 at 09:10
  • @user3161621 "doesn't affect"? Is `Animal` by any chance a `struct`? – dcastro Apr 19 '14 at 09:14
  • @dcastro I mean OP says it doesn't affect target but it would have affected `a` – Sriram Sakthivel Apr 19 '14 at 09:14
  • Oh, you mean assigning something new to `a`. I thought you meant mutating the instance's state, which could only be explained by the unboxing of `target` into `a`. – dcastro Apr 19 '14 at 09:21
  • @user3161621 - If you want to update `target` you'll have to pass it directly by changing the parameter type. – Lee Apr 19 '14 at 09:30
  • @AmitJoki - Your answer is effectively identical to my original. – Lee Apr 19 '14 at 09:31
  • @Lee, oh, yeah, except that mine is more robust, doesn't check for nulls – Amit Joki Apr 19 '14 at 09:33
  • 1
    @AmitJoki - Yours isn't more robust at all, it just does the check twice. – Lee Apr 19 '14 at 09:35
  • @Lee, twice? how. Maybe implicitly – Amit Joki Apr 19 '14 at 09:40
  • @AmitJoki - `is` and `as` are both dynamic type checks, so your answer does two while this only does one. – Lee Apr 19 '14 at 09:45
  • @AmitJoki `as` followed by null check is always better than `is` followed by `as` or `is` followed by direct cast. – Sriram Sakthivel Apr 19 '14 at 09:55
  • @SriramSakthivel, I would like to know why? – Amit Joki Apr 19 '14 at 09:56
  • @AmitJoki - The cast still requires a dynamic type check, although the `is` check before means it will not throw any exceptions. `as` already guarantees it does not throw, so is usually preferred. – Lee Apr 19 '14 at 09:56
  • @AmitJoki [Does this answers your question?](http://stackoverflow.com/questions/496096/casting-vs-using-the-as-keyword-in-the-clr/496167#496167) – Sriram Sakthivel Apr 19 '14 at 10:01
  • @Lee, yeah now I understood. So, it returns null if it isn't of type `Animal` – Amit Joki Apr 19 '14 at 10:01
  • Guys, deleted my answer, when I got to know Jon Skeet said "Don't do this". – Amit Joki Apr 19 '14 at 10:09
  • ok last question maybe i found the last problem: would unit = null; work inside my Death method? apparently all the Animal methods i use work on the ref but then when i try to "delete" it this doesnt work – user3161621 Apr 19 '14 at 10:20
  • @user3161621 - If you set `unit` to `null` inside `Death` then it will affect the ref variable in the caller. I'm not sure what you mean by "delete" though. If you have a collection of animals you can just remove the dead one from the collection and wait for it to be garbage collected if there are not more references. – Lee Apr 19 '14 at 10:31
  • yes but i would want to do it without accessing the collection (but yeah, now i think i lost enough time on this matter and ill do it like that) so i wondered if there was a sort of self destruction anyway i still dont get why in my death method unit.mymethod work on the real collection referenced while unit = null doesnt... – user3161621 Apr 19 '14 at 10:35
  • @user3161621 - There is a difference between a reference type variable and passing by reference, which you are doing here using `ref`. Copies of a reference type variable all point to the same object in memory and so can call `MyMethod` to modify it. Passing a variable by reference means that the variable in the method is an alias for the variable in the caller, so assignments to the local variable are visible in the caller. – Lee Apr 19 '14 at 10:47
1

If you mean changing the ref parameter doesn't affect target you can update manually like this.

Animal animal = target as Animal;
if(animal != null)
{
    Death(ref animal);
    target = animal;//Update it manually to target
}
Sriram Sakthivel
  • 72,067
  • 7
  • 111
  • 189
  • would you mind me asking what mistake is there in my code now? – Amit Joki Apr 19 '14 at 09:18
  • oh well this seems to be a good workaround after all, there is still a problem in my code but its unrelated (i think) but isnt there a more elegant way to do all this? – user3161621 Apr 19 '14 at 09:32
  • Basically no, because you don't have a `target` type as `Animal` so I believe there will not be any more elegant way :( If you find any pls let us know.. – Sriram Sakthivel Apr 19 '14 at 09:36