本文介绍了C#ref是C/C ++中的指针还是C ++中的引用?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我正在使用ref,但不清楚地理解它像C/C ++中的指针一样,还是像C ++中的引用一样?"

I'm working with the ref and don't understand clearly "Is it like a pointer as in C/C++ or it's like a reference in C++?"

为什么我问了你一会儿这么弱的问题?因为,当我阅读C#/.NET书籍,msdn或与C#开发人员交谈时,由于以下原因,我感到困惑:

Why did I ask such a weak question as you thought for a moment?Because, when I'm reading C#/.NET books, msdn or talking to C# developers I'm becoming confused by the following reasons:

  • C#开发人员建议不要在函数的参数中使用refe.g. ...(ref Type someObject)不会对他们有好处,他们建议...(Type someObject),我真的不太清楚这个建议.我听到的原因:更好地使用对象的副本,然后将其用作返回值,而不是通过引用破坏内存等.通常,我会听到有关DB连接对象的此类解释.像我平常的C/C ++经验一样,我真的不明白为什么在C#中使用引用是不好的事情?我控制对象的寿命及其内存分配/重新分配等...我在书籍和论坛上阅读的内容仅建议it's bad, because you can corrupt your connection and cause a memory leak by a reference lose,因此我控制了对象的寿命,我可能手动控制了我真正想要的东西,所以为什么是不好吗?
  • 如今阅读不同的书籍并与不同的人交谈,我不清楚是ref是指针(*)还是&在C ++中的引用?我记得C/C ++中的指针总是分配大小为void*类型的空间-4个字节(有效大小取决于体系结构),在该空间中托管结构或变量的地址.在C ++中,通过传递引用&,没有来自堆/堆栈的新分配,并且您已经在内存空间中使用了已定义的对象,并且没有像普通C那样从外部为指针进行子分配的内存.所以在C#中? .NET VM是否像普通C/C ++中的指针一样处理它,并且它的GC为指针分配临时空间,还是像C ++中的引用一样工作? ref是否仅正确使用托管类型或对于bool, int之类的值类型,最好切换unsafe代码并以非托管样式传递指针?
  • C# developers suggest NOT to use ref in the arguments of a function, e.g. ...(ref Type someObject) doesn't smell good for them and they suggest ...(Type someObject), I really don't understand clearly this suggestion. The reasons I heard: better to work with the copy of object, then use it as a return value, not to corrupt memory by a reference etc... Often I hear such explanation about DB connection objects. As on my plain C/C++ experience, I really don't understand why to use a reference is a bad stuff in C#? I control the life of object and its memory allocations/re-allocations etc... I read in books and forums only advises it's bad, because you can corrupt your connection and cause a memory leak by a reference lose, so I control the life of object, I may control manually what I really want, so why is it bad?
  • Nowadays reading different books and talk to different people, I don't clearly understand is ref a pointer (*) or a reference like in C++ by & ? As I remember pointers in C/C++ always do allocate a space with a size of void* type - 4 bytes (the valid size depends on architecture), where hosts an address to a structure or variable. In C++ by passing a reference & there is no new allocations from the heap/stack and you work with already defined objects in memory space and there is no sub-allocating memory for a pointer externally like in plain C. So what's the ref in C#? Does .NET VM handle it like a pointer in plain C/C++ and its GC allocates temporary space for a pointer or it does a work like reference in C++? Does ref work only with a managed types correctly or for value types like bool, int it's better to switch an unsafe code and pass through a pointer in unmanaged style?

推荐答案

在C#中,当看到引用引用类型的内容(即用class而不是struct声明的类型)时,您将本质上,总是通过指针处理对象.在C ++中,默认情况下,所有内容都是值类型,而在C#中,默认情况下,所有内容都是引用类型.

In C#, when you see something referring to a reference type (that is, a type declared with class instead of struct), then you're essentially always dealing with the object through a pointer. In C++, everything is a value type by default, whereas in C# everything is a reference type by default.

在C#参数列表中说"ref"时,您实际上所说的更像是指向指针的指针".您说的是,在方法中,您不想在调用方法的代码中替换对象的内容,而是替换对象本身的引用.

When you say "ref" in the C# parameter list, what you're really saying is more like a "pointer to a pointer." You're saying that, in the method, that you want to replace not the contents of the object, but the reference to the object itself, in the code calling your method.

除非您的意图是,否则您应该直接传递引用类型;否则,您应该直接传递引用类型.在C#中,传递引用类型很便宜(类似于在C ++中传递引用).

Unless that is your intent, then you should just pass the reference type directly; in C#, passing reference types around is cheap (akin to passing a reference in C++).

了解/理解C#中的值类型和引用类型之间的区别.它们是该语言的主要概念,如果您尝试考虑在C#领域中使用C ++对象模型,事情将变得非常混乱.

Learn/understand the difference between value types and reference types in C#. They're a major concept in that language and things are going to be really confusing if you try to think using the C++ object model in C# land.

以下是在语义上等效的程序:

The following are essentially semantically equivalent programs:

#include <iostream>

class AClass
{
    int anInteger;
public:
    AClass(int integer)
        : anInteger(integer)
    {  }

    int GetInteger() const
    {
        return anInteger;
    }

    void SetInteger(int toSet)
    {
        anInteger = toSet;
    }
};

struct StaticFunctions
{
    // C# doesn't have free functions, so I'll do similar in C++
    // Note that in real code you'd use a free function for this.

    static void FunctionTakingAReference(AClass *item)
    {
        item->SetInteger(4);
    }

    static void FunctionTakingAReferenceToAReference(AClass **item)
    {
        *item = new AClass(1729);
    }
};

int main()
{
    AClass* instanceOne = new AClass(6);
    StaticFunctions::FunctionTakingAReference(instanceOne);
    std::cout << instanceOne->GetInteger() << "\n";

    AClass* instanceTwo;
    StaticFunctions::FunctionTakingAReferenceToAReference(&instanceTwo);
    // Note that operator& behaves similar to the C# keyword "ref" at the call site.
    std::cout << instanceTwo->GetInteger() << "\n";

    // (Of course in real C++ you're using std::shared_ptr and std::unique_ptr instead,
    //  right? :) )
    delete instanceOne;
    delete instanceTwo;
}

对于C#:

using System;

internal class AClass
{
    public AClass(int integer)
        : Integer(integer)
    {  }

    int Integer { get; set; }
}

internal static class StaticFunctions
{
    public static void FunctionTakingAReference(AClass item)
    {
        item.Integer = 4;
    }

    public static void FunctionTakingAReferenceToAReference(ref AClass item)
    {
        item = new AClass(1729);
    }
}

public static class Program
{
    public static void main()
    {
        AClass instanceOne = new AClass(6);
        StaticFunctions.FunctionTakingAReference(instanceOne);
        Console.WriteLine(instanceOne.Integer);

        AClass instanceTwo  = new AClass(1234); // C# forces me to assign this before
                                                // it can be passed. Use "out" instead of
                                                // "ref" and that requirement goes away.
        StaticFunctions.FunctionTakingAReferenceToAReference(ref instanceTwo);
        Console.WriteLine(instanceTwo.Integer);
    }
}

这篇关于C#ref是C/C ++中的指针还是C ++中的引用?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持!

08-19 15:06