Sign Up

Sign Up to our social questions and Answers Engine to ask questions, answer people’s questions, and connect with other people.

Have an account? Sign In

Have an account? Sign In Now

Sign In

Login to our social questions & Answers Engine to ask questions answer people’s questions & connect with other people.

Sign Up Here

Forgot Password?

Don't have account, Sign Up Here

Forgot Password

Lost your password? Please enter your email address. You will receive a link and will create a new password via email.

Have an account? Sign In Now

You must login to ask a question.

Forgot Password?

Need An Account, Sign Up Here

Please briefly explain why you feel this question should be reported.

Please briefly explain why you feel this answer should be reported.

Please briefly explain why you feel this user should be reported.

Sign InSign Up

The Archive Base

The Archive Base Logo The Archive Base Logo

The Archive Base Navigation

  • SEARCH
  • Home
  • About Us
  • Blog
  • Contact Us
Search
Ask A Question

Mobile menu

Close
Ask a Question
  • Home
  • Add group
  • Groups page
  • Feed
  • User Profile
  • Communities
  • Questions
    • New Questions
    • Trending Questions
    • Must read Questions
    • Hot Questions
  • Polls
  • Tags
  • Badges
  • Buy Points
  • Users
  • Help
  • Buy Theme
  • SEARCH
Home/ Questions/Q 959359
In Process

The Archive Base Latest Questions

Editorial Team
  • 0
Editorial Team
Asked: May 16, 20262026-05-16T01:00:44+00:00 2026-05-16T01:00:44+00:00

Can someone please explain me the following code snippet? value struct ValueStruct { int

  • 0

Can someone please explain me the following code snippet?

value struct ValueStruct {
    int x;
};

void SetValueOne(ValueStruct% ref) {
    ref.x = 1;
}

void SetValueTwo(ValueStruct ref) {
    ref.x = 2;
}

void SetValueThree(ValueStruct^ ref) {
    ref->x = 3;
}

ValueStruct^ first = gcnew ValueStruct;
first->x = 0;
SetValueOne(*first);

ValueStruct second;
second.x = 0;
SetValueTwo(second); // am I creating a copy or what? is this copy Disposable even though value types don't have destructors?

ValueStruct^ third = gcnew ValueStruct;
third->x = 0;
SetValueThree(third); // same as the first ?

And my second question is: is there any reason to have something like that?:

ref struct RefStruct {
    int x;
};

RefStruct% ref = *gcnew RefStruct;
// rather than:
// RefStruct^ ref = gcnew RefStruct;

// can I retrieve my handle from ref?
// RefStruct^ myref = ???

What is more: I see no difference between value type and ref type, since both can be pointed by handler ;(

  • 1 1 Answer
  • 0 Views
  • 0 Followers
  • 0
Share
  • Facebook
  • Report

Leave an answer
Cancel reply

You must login to add an answer.

Forgot Password?

Need An Account, Sign Up Here

1 Answer

  • Voted
  • Oldest
  • Recent
  • Random
  1. Editorial Team
    Editorial Team
    2026-05-16T01:00:45+00:00Added an answer on May 16, 2026 at 1:00 am

    Remember that the primary use of C++/CLI is for developing class libraries for consumption by GUIs / web services built in other .NET languages. So C++/CLI has to support both reference and value types because other .NET languages do.

    Furthermore, C# can have ref parameters that are value typed as well, this isn’t unique to C++/CLI and it doesn’t in any way make value types equivalent to reference types.

    To answer the questions in your code comments:

    am I creating a copy or what?

    Yes, SetValueTwo takes its parameter by value, so a copy is made.

    is this copy Disposable even though value types don’t have destructors?

    Incorrect. Value types can have destructors. Value types cannot have finalizers. Since this particular value type has a trivial destructor, the C++/CLI compiler will not cause it to implement IDisposable. In any case, if a parameter is an IDisposable value type, the C++/CLI compiler will ensure that Dispose is called when the variable goes out of scope, just like stack semantics for local variables. This includes abnormal termination (thrown exception), and allows managed types to be used with RAII.

    Both

    ValueStruct% ref = *gcnew ValueStruct;
    

    and

    ValueStruct^ ref = gcnew ValueStruct;
    

    are allowed, and put a boxed value type instance on the managed heap (which isn’t a heap at all, but a FIFO queue, however Microsoft chooses to call it a heap like the native memory area for dynamic allocation).

    Unlike C#, C++/CLI can keep typed handles to boxed objects.

    If a tracking reference is to a value type instance on the stack or embedded in another object, then the value type content has to be boxed in the process of formed the reference.

    Tracking references can also be used with reference types, and the syntax to obtain a handle is the same:

    RefClass^ newinst = gcnew RefClass();
    RefClass% reftoinst = *newinst;
    RefClass^% reftohandle = newinst;
    
    RefClass stacksem;
    RefClass^ ssh = %stacksem;
    

    One thing that I can never seem to remember completely is that the syntax isn’t 100% consistent compared to native C++.

    Declare a reference:

    int& ri = i; // native
    DateTime% dtr = dt; // managed tracking reference
    

    Declare a pointer:

    int* pi; // native
    Stream^ sh; // tracking handle
    

    Form a pointer:

    int* pi = &ri; // address-of native object
    DateTime^ dth = %dtr; // address-of managed object
    

    Note that the unary address-of operator is the same as the reference notation in both standard C++ and C++/CLI. This seems to contradict a tracking reference cannot be used as a unary take-address operator (MSDN) which I’ll get back to in a second.

    First though, the inconsistency:

    Form a reference from a pointer:

    int& iref = *pi;
    DateTime% dtref = *dth;
    

    Note that the unary dereference operator is always *. It is the same as the pointer notation only in the native world, which is completely opposite of address-of which, as mentioned above, are always the same symbol as the reference notation.

    Compilable example:

    DateTime^ dth = gcnew DateTime();
    DateTime% dtr = *dth;
    
    DateTime dt = DateTime::Now;
    DateTime^ dtbox = %dt;
    
    FileInfo fi("temp.txt");
    // FileInfo^ fih = &fi;  causes error C3072
    FileInfo^ fih = %fi;
    

    Now, about unary address-of:

    First, the MSDN article is wrong when it says:

    The following sample shows that a tracking reference cannot be used as a unary take-address operator.

    The correct statement is:

    % is the address-of operator for creation of a tracking handle. However its use is limited as follows:

    A tracking handle must point to an object on the managed heap. Reference types always exist on the managed heap so there is no problem. However, value types and native types may be on the stack (for local variables) or embedded within another object (member variables of value type). Attempts to form a tracking handle will form a handle to a boxed copy of the variable: the handle is not linked to the original variable. As a consequence of the boxing process, which requires metadata which does not exist for native types, it is never possible to have a tracking handle to an instance of a native type.

    Example code:

    int i = 5;
    // int^ ih = %i;  causes error C3071
    
    System::Int32 si = 5;
    // System::Int32^ sih = %si; causes error C3071
    // error C3071: operator '%' can only be applied to an instance 
    //              of a ref class or a value-type
    

    If System::Int32 isn’t a value type then I don’t know what is. Let’s try System::DateTime which is a non-primitive value type:

    DateTime dt = DateTime::Now;
    DateTime^ dtbox = %dt;
    

    This works!

    As a further unfortunate restriction, primitive types which have dual identity (e.g. native int and managed value type System::Int32) are not handled correctly, the % (form tracking reference) operator cannot perform boxing even when the .NET name for the type is given.

    • 0
    • Reply
    • Share
      Share
      • Share on Facebook
      • Share on Twitter
      • Share on LinkedIn
      • Share on WhatsApp
      • Report

Sidebar

Ask A Question

Stats

  • Questions 506k
  • Answers 506k
  • Best Answers 0
  • User 1
  • Popular
  • Answers
  • Editorial Team

    How to approach applying for a job at a company ...

    • 7 Answers
  • Editorial Team

    How to handle personal stress caused by utterly incompetent and ...

    • 5 Answers
  • Editorial Team

    What is a programmer’s life like?

    • 5 Answers
  • Editorial Team
    Editorial Team added an answer Session.Abandon(); The Abandon method destroys all the objects stored in… May 16, 2026 at 3:36 pm
  • Editorial Team
    Editorial Team added an answer Maybe case sensitive May 16, 2026 at 3:36 pm
  • Editorial Team
    Editorial Team added an answer I actually got to the source of the problem. It… May 16, 2026 at 3:36 pm

Trending Tags

analytics british company computer developers django employee employer english facebook french google interview javascript language life php programmer programs salary

Top Members

Related Questions

Can someone please explain why the following code causes my app to bomb? NSData
Can someone please explain the following Argument Exception : The structure must not be
Can someone please explain (what might be my perceived) disparity in errors in the
Can someone please explain to me once and for good what are Session Key
Can someone please explain to me what goes to the Output window in VS?
Could someone explain this behaviour to me? If you execute the snippet at the
I have the following code that I expect to run successfully to completion but
I have came across the following code, and being a C beginner, I came
I am using the following code to fire the iexplore process. This is done
The following code is creating problem. var_dump($name); $name = mb_strtolower($name); var_dump($name); Output is string(32)

Explore

  • Home
  • Add group
  • Groups page
  • Communities
  • Questions
    • New Questions
    • Trending Questions
    • Must read Questions
    • Hot Questions
  • Polls
  • Tags
  • Badges
  • Users
  • Help
  • SEARCH

Footer

© 2021 The Archive Base. All Rights Reserved
With Love by The Archive Base

Insert/edit link

Enter the destination URL

Or link to existing content

    No search term specified. Showing recent items. Search or use up and down arrow keys to select an item.