ValueType reference in objects

  • Thread starter Thread starter Guest
  • Start date Start date
G

Guest

Hi all,

With the followin code:

class MyClass
{
public int i;
public MyClass(ref int I)
{
i = I;
}
}

class Program
{
static void Main(string[] args)
{
int i = 50;
MyClass c = new MyClass(ref i);
Console.WriteLine(c.i);

i = 10;
Console.WriteLine(c.i);

Console.ReadLine();
}
}

I´ve got:

50
50

The i field from c object didn´t change its value.
The i field doesn´t point to i address.

C# copies the value from the i variable to the object heap field i.
Is this correct? Heap object doesn´t point to stack variables?

Please help.

TIA,
 
Andre Azevedo said:
C# copies the value from the i variable to the object heap field i.
Is this correct? Heap object doesn´t point to stack variables?

No, it doesn't. There might be a way to generate a reference to a local
variable, but if there is I don't know what it is, and for sure the code you
posted doesn't. Except, of course, as the "by reference" parameter in the
constructor...but in that case, you still can't access the reference
directly, it just means that if you change the value of the parameter in the
constructor, the original variable passed in is changed as well. That
behavior does not extend to other values to which the parameter is assigned.

Pete
 
Hey Andre...
public MyClass(ref int I)
{
i = I;
}
... SNIP ...
C# copies the value from the i variable to the object heap field i.
Is this correct? Heap object doesn´t point to stack variables?

Value of I is copied to the location of i. Indeed, since MyClass is a
class, its memory is allocated on the heap. But because i is int, a
value type, the "=" operator copies its content, and does not assign
it's location (address).

Note: This is true for strings too, although they are reference types.
The "=" operator for strings is implemented to behave like a the
assignment of a value type.

Does this answer your question?

David
 
Hey

You could try creating a custom integer class and pass it to the your
cons instead of int
 
If your goal is to simply find a way to pass in integer pointers, then the
following code will work. I would like to point out that using pointers and
unsafe code is NOT recommended and should be reserved for special case
scenarioes.

You will also need to check the "Allow unsafe code" option in the Build tab
of your project properties.

unsafe class MyClass
{
public int* i;
public MyClass(int* I)
{
i = I;
}
}

class Program
{
unsafe static void Main(string[] args)
{
int i = 50;
MyClass c = new MyClass(&i);
Console.WriteLine(*c.i);

i = 10;
Console.WriteLine(*c.i);

Console.ReadLine();
}
}

HTH :-)
--
Good luck!

Shailen Sukul
Architect
(BSc MCTS, MCSD.Net MCSD MCAD)
Ashlen Consulting Service P/L
(http://www.ashlen.net.au)
 
Yes.
Thanks!

David Boucherie & Co said:
Hey Andre...


Value of I is copied to the location of i. Indeed, since MyClass is a
class, its memory is allocated on the heap. But because i is int, a value
type, the "=" operator copies its content, and does not assign it's
location (address).

Note: This is true for strings too, although they are reference types. The
"=" operator for strings is implemented to behave like a the assignment of
a value type.

Does this answer your question?

David
 
Hi,

I just ask because I really didn't know what happens with my code.
I have a thread that polls hardware events in a loop calling an unmanaged
function. The event structure has unions with value and reference types and
to receive the event structure I use IntPtr: (non-blittable)

For instance:

int eventSize = 0;
IntPtr event;

while(threadActive)
{

event = Marshal.AllocHGlobal(256);

int result = StaticClass.UnmanagedFunction(IntPtr event, ref eventSize);
....
(parse IntPtr)
...

Marshal.FreeHGlobal(event);

}

Now, I want to parse the event variable asynchronously. So I have to
encapsulate it in some class and this class is passe in
ThreadPool.QueueUserWorkItem method:

{
....
event = Marshal.AllocHGlobal(256);
int result = StaticClass.UnmanagedFunction(IntPtr event, ref eventSize);

MyContainerClass c = new MyContainerClass(ref IntPtr); <----- What happes
here!
ThreadPool.QueueUserWorkItem(new WaitCallback(MyWaitCallBackMethod),
MyContainerClass);
....
}

void MyWaitCallBackMethod(object state)
{

MyContainerClass c = (MyContainerClass) state;
IntPtr event = c.event;
...
(parse IntPtr)
...
Marshal.FreeHGlobal(event);

}

That's why I ask about "ref" value parameters.
Thanks!

--
Andre Azevedo


Shailen Sukul said:
If your goal is to simply find a way to pass in integer pointers, then the
following code will work. I would like to point out that using pointers
and
unsafe code is NOT recommended and should be reserved for special case
scenarioes.

You will also need to check the "Allow unsafe code" option in the Build
tab
of your project properties.

unsafe class MyClass
{
public int* i;
public MyClass(int* I)
{
i = I;
}
}

class Program
{
unsafe static void Main(string[] args)
{
int i = 50;
MyClass c = new MyClass(&i);
Console.WriteLine(*c.i);

i = 10;
Console.WriteLine(*c.i);

Console.ReadLine();
}
}

HTH :-)
--
Good luck!

Shailen Sukul
Architect
(BSc MCTS, MCSD.Net MCSD MCAD)
Ashlen Consulting Service P/L
(http://www.ashlen.net.au)


Andre Azevedo said:
Hi all,

With the followin code:

class MyClass
{
public int i;
public MyClass(ref int I)
{
i = I;
}
}

class Program
{
static void Main(string[] args)
{
int i = 50;
MyClass c = new MyClass(ref i);
Console.WriteLine(c.i);

i = 10;
Console.WriteLine(c.i);

Console.ReadLine();
}
}

I´ve got:

50
50

The i field from c object didn´t change its value.
The i field doesn´t point to i address.

C# copies the value from the i variable to the object heap field i.
Is this correct? Heap object doesn´t point to stack variables?

Please help.

TIA,
 
David Boucherie & Co said:
Note: This is true for strings too, although they are reference types.
The "=" operator for strings is implemented to behave like a the
assignment of a value type.

There's nothing special about how "=" is handled with strings. It's the
same as with every other reference type - it just copies the reference.

Strings just happen to be immutable, so things like Replace return a
reference to a new string, and if you do:

x += "fred";

that is the same as:

x = x + "fred";

where x + "fred" returns a new string which is the concatenation of x
and "fred".

Nothing special at all in there. Note that in fact you can't overload
the "=" operator in C# (fortunately, IMO).
 
That's why I ask about "ref" value parameters.

"ref" only makes a difference if you change the *parameter* during the
method. Other than that, it behaves just like any other parameter. In
particular:

myVariable = myParameter;

is just a copy of the value of myParameter to myVariable, whether the
myParameter parameter is passed by reference or not. There's no "link"
forged between myVariable and myParameter.

See http://www.pobox.com/~skeet/csharp/parameters.html for more on
parameter passing.
 
Back
Top