c#语言中,结构体和类的区别?
在C#语言中,“结构体”和“类”有啥区别?怎样辨别是结构体还是类!两者里面是不是都有构造函数?为什么结构体用得比较少?望c#高手指点,谢谢!我把“结构体”、“类”、“构造...
在C#语言中,“结构体”和“类”有啥区别?怎样辨别是结构体还是类!两者里面是不是都有构造函数?为什么结构体用得比较少?望c#高手指点,谢谢!我把“结构体”、“类”、“构造函数”这三种搞混了,有点分不清,麻烦给讲解下!真的谢谢了。。。。。
展开
6个回答
展开全部
1,结构是实值类型(Value Types),而类则是引用类型(Reference Types)。
2,结构使用栈存储(Stack Allocation),而类使用堆存储(Heap Allocation)。
3,所有结构成员默认都是Public,而类的变量和常量数则默认位Private,不过其他类成员默认都是Public。
4,结构成员不能被声明位Protected,而类成员可以。
5,结构变量声明不能指定初始值、使用New关键字货对数组进行初始化,但是类变量声明可以。
6,结构不能声明默认的构造函数,也就是不拥有参数的非共享构造函数,但是类则无此限制。
7,二者都可以拥有共享构造函数,结构的共享构造函数不能带有参数,但是类的共享构造函数则可以带或者不带参数。
8,结构不允许声明析构函数(Destructor),类则无此限制。
9,结构的实例(Instance)声明,不允许对包含的变量进行初始化设定,类则可以在声明类的实例时,同时进行变量初始化。
10,结构是隐式继承自ValueType类,而且不能继承任何其他类型,类则可以继续自ValueType以外的任何类。
11,结构是无法被继承的,类则可以。
12,结构永远不会终止,因此CLR不会在任何结构上调用Finalize方法。类则是由内存回收进程加以终止,当内存回收进程检测到没有任何作用的类时,它就会调用类的Finalize方法。
13,结构不需要构造函数,类则需要构造函数。
14,结构只能在一种情况下使用非共享构造函数,那就是非共享构造函数会接受参数。但是类则无此限制,它可以使用带参数或不带参数的非共享构造函数。
14,每一个结构都具有无参数的隐含公共构造函数,此构造函数会将结构的所有成员初始化为其默认值。不需要重新定义这个行为。
在“实例和变量”层面上,由于结构是数值类型的,因此每一个结构变量会永远的绑定到结构实例上。然而类是引用类型的,而且对象变量可引用不同的类实例,在此方面的区别,会对使用将结构和类造成如下的影响:
15,结构变量会隐式的使用结构的无参数构造函数来初始化成员,这就意味语句 Struct S = new Struct()。
16,当您将一个结构变量赋值给另一个,或者将结构实例传递到程序变量时,所有变量成员的值会复制到新的结构中。当您将一个对象变量赋值给另一个,或者将对象变量传递给程序时,则只是复制指针。
17,您可以将Null值赋值给结构变量,但是该实例会一直与该变量保持关联。虽然变量成员会因此赋值而重新初始化,但是您还是可以调用变量的方法并访问其数据成员。相反的,如果您将对象变量设定为Null,您就会中断它与任何类型实例的关联,而且除非您再将另一个实例赋值给它,否则无法通过变量访问任何成员。
18,您可以在不同时间将不同的类的实例赋值给同一个对象变量,而且在同一时间可有好几个对象变量引用相同的类实例,如果您对类成员值做了改变,则其他指向相同实例的对象变量也会发生改变。然而,结构成员则会封装在他们自己的实例中,变更结构成员值并不会对其他任何结构变量的成员造成影响,甚至也不会影响相同结构声明的其他实例。
19,两个结构必须以成员对成员的比较方式来执行相等比较。两个对象变量可以使用Equals方法来加以比较。Equals会判断两个变量是否指向相同的实例。
2,结构使用栈存储(Stack Allocation),而类使用堆存储(Heap Allocation)。
3,所有结构成员默认都是Public,而类的变量和常量数则默认位Private,不过其他类成员默认都是Public。
4,结构成员不能被声明位Protected,而类成员可以。
5,结构变量声明不能指定初始值、使用New关键字货对数组进行初始化,但是类变量声明可以。
6,结构不能声明默认的构造函数,也就是不拥有参数的非共享构造函数,但是类则无此限制。
7,二者都可以拥有共享构造函数,结构的共享构造函数不能带有参数,但是类的共享构造函数则可以带或者不带参数。
8,结构不允许声明析构函数(Destructor),类则无此限制。
9,结构的实例(Instance)声明,不允许对包含的变量进行初始化设定,类则可以在声明类的实例时,同时进行变量初始化。
10,结构是隐式继承自ValueType类,而且不能继承任何其他类型,类则可以继续自ValueType以外的任何类。
11,结构是无法被继承的,类则可以。
12,结构永远不会终止,因此CLR不会在任何结构上调用Finalize方法。类则是由内存回收进程加以终止,当内存回收进程检测到没有任何作用的类时,它就会调用类的Finalize方法。
13,结构不需要构造函数,类则需要构造函数。
14,结构只能在一种情况下使用非共享构造函数,那就是非共享构造函数会接受参数。但是类则无此限制,它可以使用带参数或不带参数的非共享构造函数。
14,每一个结构都具有无参数的隐含公共构造函数,此构造函数会将结构的所有成员初始化为其默认值。不需要重新定义这个行为。
在“实例和变量”层面上,由于结构是数值类型的,因此每一个结构变量会永远的绑定到结构实例上。然而类是引用类型的,而且对象变量可引用不同的类实例,在此方面的区别,会对使用将结构和类造成如下的影响:
15,结构变量会隐式的使用结构的无参数构造函数来初始化成员,这就意味语句 Struct S = new Struct()。
16,当您将一个结构变量赋值给另一个,或者将结构实例传递到程序变量时,所有变量成员的值会复制到新的结构中。当您将一个对象变量赋值给另一个,或者将对象变量传递给程序时,则只是复制指针。
17,您可以将Null值赋值给结构变量,但是该实例会一直与该变量保持关联。虽然变量成员会因此赋值而重新初始化,但是您还是可以调用变量的方法并访问其数据成员。相反的,如果您将对象变量设定为Null,您就会中断它与任何类型实例的关联,而且除非您再将另一个实例赋值给它,否则无法通过变量访问任何成员。
18,您可以在不同时间将不同的类的实例赋值给同一个对象变量,而且在同一时间可有好几个对象变量引用相同的类实例,如果您对类成员值做了改变,则其他指向相同实例的对象变量也会发生改变。然而,结构成员则会封装在他们自己的实例中,变更结构成员值并不会对其他任何结构变量的成员造成影响,甚至也不会影响相同结构声明的其他实例。
19,两个结构必须以成员对成员的比较方式来执行相等比较。两个对象变量可以使用Equals方法来加以比较。Equals会判断两个变量是否指向相同的实例。
展开全部
第一个问题:,“结构体”和“类”有啥区别?怎样辨别是结构体还是类!
结构体是一种值类型,而类是引用类型。(值类型、引用类型是根据数据存储的角度来分的)
就是值类型用于存储数据的值,引用类型用于存储对实际数据的引用。那么结构体就是当成值来使用的,类则通过引用来对实际数据操作。
第二个问题:两者里面是不是都有构造函数?为什么结构体用得比较少?
构造函数是为了初始化类的字段而存在的,而结构体并不需要初始化就能使用,因此,结构体中并不存在构造函数。
不能以使用多少来衡量,只是看相应问题使用最适合的方法罢了。结构体的定义是:有些数据既是相互关联的,又共同描述一个完整事物,如:一个学生的整体信息,学号、姓名、性别等。而类则使用在需要比较有层次的数据上面。
结构体是一种值类型,而类是引用类型。(值类型、引用类型是根据数据存储的角度来分的)
就是值类型用于存储数据的值,引用类型用于存储对实际数据的引用。那么结构体就是当成值来使用的,类则通过引用来对实际数据操作。
第二个问题:两者里面是不是都有构造函数?为什么结构体用得比较少?
构造函数是为了初始化类的字段而存在的,而结构体并不需要初始化就能使用,因此,结构体中并不存在构造函数。
不能以使用多少来衡量,只是看相应问题使用最适合的方法罢了。结构体的定义是:有些数据既是相互关联的,又共同描述一个完整事物,如:一个学生的整体信息,学号、姓名、性别等。而类则使用在需要比较有层次的数据上面。
本回答被提问者采纳
已赞过
已踩过<
评论
收起
你对这个回答的评价是?
展开全部
c#中结构与类的区
目录
类与结构的实例比较
类与结构的差别
如何选择结构还是类
一.类与结构的示例比较:
结构示例:
public struct Person
{
string Name;
int height;
int weight
public bool overWeight()
{
//implement something
}
}
类示例:
public class TestTime
{
int hours;
int minutes;
int seconds;
public void passtime()
{
//implementation of behavior
}
}
调用过程:
public class Test
{
public static ovid Main
{
Person Myperson=new Person //声明结构
TestTime Mytime=New TestTime //声明类
}
}
从上面的例子中我们可以看到,类的声明和结构的声明非常类似,只是限定符后面是 struct 还是 class 的区别,而且使用时,定义新的结构和定义新的类的方法也非常类似。那么类和结构的具体区别是什么呢?
二 .类与结构的差别
1. 值类型与引用类型
结构是值类型:值类型在堆栈上分配地址,所有的基类型都是结构类型,例如:int 对应System.int32 结构,string 对应 system.string 结构 ,通过使用结构可以创建更多的值类型
类是引用类型:引用类型在堆上分配地址
堆栈的执行效率要比堆的执行效率高,可是堆栈的资源有限,不适合处理大的逻辑复杂的对象。所以结构处理作为基类型对待的小对象,而类处理某个商业逻辑
因为结构是值类型所以结构之间的赋值可以创建新的结构,而类是引用类型,类之间的赋值只是复制引用
注:
1.虽然结构与类的类型不一样,可是他们的基类型都是对象(object),c#中所有类型的基类型都是object
2.虽然结构的初始化也使用了New 操作符可是结构对象依然分配在堆栈上而不是堆上,如果不使用“新建”(new),那么在初始化所有字段之前,字段将保持未赋值状态,且对象不可用
2.继承性
结构:不能从另外一个结构或者类继承,本身也不能被继承,虽然结构没有明确的用sealed声明,可是结构是隐式的sealed .
类:完全可扩展的,除非显示的声明sealed 否则类可以继承其他类和接口,自身也能被继承
注:虽然结构不能被继承 可是结构能够继承接口,方法和类继承接口一样
例如:结构实现接口
interface IImage
{
void Paint();
}
struct Picture : IImage
{
public void Paint()
{
// painting code goes here
}
private int x, y, z; // other struct members
}
3.内部结构:
结构:
没有默认的构造函数,但是可以添加构造函数
没有析构函数
没有 abstract 和 sealed(因为不能继承)
不能有protected 修饰符
可以不使用new 初始化
在结构中初始化实例字段是错误的
类:
有默认的构造函数
有析构函数
可以使用 abstract 和 sealed
有protected 修饰符
必须使用new 初始化
三.如何选择结构还是类
讨论了结构与类的相同之处和差别之后,下面讨论如何选择使用结构还是类:
1. 堆栈的空间有限,对于大量的逻辑的对象,创建类要比创建结构好一些
2. 结构表示如点、矩形和颜色这样的轻量对象,例如,如果声明一个含有 1000 个点对象的数组,则将为引用每个对象分配附加的内存。在此情况下,结构的成本较低。
3. 在表现抽象和多级别的对象层次时,类是最好的选择
4. 大多数情况下该类型只是一些数据时,结构时最佳的选择
目录
类与结构的实例比较
类与结构的差别
如何选择结构还是类
一.类与结构的示例比较:
结构示例:
public struct Person
{
string Name;
int height;
int weight
public bool overWeight()
{
//implement something
}
}
类示例:
public class TestTime
{
int hours;
int minutes;
int seconds;
public void passtime()
{
//implementation of behavior
}
}
调用过程:
public class Test
{
public static ovid Main
{
Person Myperson=new Person //声明结构
TestTime Mytime=New TestTime //声明类
}
}
从上面的例子中我们可以看到,类的声明和结构的声明非常类似,只是限定符后面是 struct 还是 class 的区别,而且使用时,定义新的结构和定义新的类的方法也非常类似。那么类和结构的具体区别是什么呢?
二 .类与结构的差别
1. 值类型与引用类型
结构是值类型:值类型在堆栈上分配地址,所有的基类型都是结构类型,例如:int 对应System.int32 结构,string 对应 system.string 结构 ,通过使用结构可以创建更多的值类型
类是引用类型:引用类型在堆上分配地址
堆栈的执行效率要比堆的执行效率高,可是堆栈的资源有限,不适合处理大的逻辑复杂的对象。所以结构处理作为基类型对待的小对象,而类处理某个商业逻辑
因为结构是值类型所以结构之间的赋值可以创建新的结构,而类是引用类型,类之间的赋值只是复制引用
注:
1.虽然结构与类的类型不一样,可是他们的基类型都是对象(object),c#中所有类型的基类型都是object
2.虽然结构的初始化也使用了New 操作符可是结构对象依然分配在堆栈上而不是堆上,如果不使用“新建”(new),那么在初始化所有字段之前,字段将保持未赋值状态,且对象不可用
2.继承性
结构:不能从另外一个结构或者类继承,本身也不能被继承,虽然结构没有明确的用sealed声明,可是结构是隐式的sealed .
类:完全可扩展的,除非显示的声明sealed 否则类可以继承其他类和接口,自身也能被继承
注:虽然结构不能被继承 可是结构能够继承接口,方法和类继承接口一样
例如:结构实现接口
interface IImage
{
void Paint();
}
struct Picture : IImage
{
public void Paint()
{
// painting code goes here
}
private int x, y, z; // other struct members
}
3.内部结构:
结构:
没有默认的构造函数,但是可以添加构造函数
没有析构函数
没有 abstract 和 sealed(因为不能继承)
不能有protected 修饰符
可以不使用new 初始化
在结构中初始化实例字段是错误的
类:
有默认的构造函数
有析构函数
可以使用 abstract 和 sealed
有protected 修饰符
必须使用new 初始化
三.如何选择结构还是类
讨论了结构与类的相同之处和差别之后,下面讨论如何选择使用结构还是类:
1. 堆栈的空间有限,对于大量的逻辑的对象,创建类要比创建结构好一些
2. 结构表示如点、矩形和颜色这样的轻量对象,例如,如果声明一个含有 1000 个点对象的数组,则将为引用每个对象分配附加的内存。在此情况下,结构的成本较低。
3. 在表现抽象和多级别的对象层次时,类是最好的选择
4. 大多数情况下该类型只是一些数据时,结构时最佳的选择
参考资料: http://wenku.baidu.com/view/fafcf7ebe009581b6bd9ebb8.html
已赞过
已踩过<
评论
收起
你对这个回答的评价是?
展开全部
看到你问的问题就知道你是初学者。
首选结构体是一个值类型,而类是一个引用类型。
从你的后几句的补充上来说,你还没有型清楚什么是引用类型,什么是值类型。字与传值引用,传址引用是两码事,不要弄一块了!
所以的值类型与引用类型上,我这样给你说一下,看你是否能明白。
值类型的内存单元里是值,而引用类型单元里边是地址,地址指向了值。
比如int是值类型,int
s
=5;
s这个内存单元中就是5,不是地址指针。
而类则是一种引用类型!类中的并不是实际的值,而是一些指针指向了真正的值。
所以值类型就是反映的直接的数据。如:
struct
M(int,int)
这个结构就是直接的值类型,它在内存中的表现是,除了结果体说明,就占两个int空间,用第一个空间里的数做第一个数值,第二个空间的数就是第一个数值。这就是结构体,也就是值类型。
值类型与引用类型说是类型。
传值引用,与址引用说的是引用方式。我给你的参数是一个值,你就按这个类计算去。如果我给的是地址,你计算时直接用的是地址。
在C#中没有传址,而是直接使用的ref参数与out参数将对象直接传入的。
传址引用与传值引用是两种不同的引用方式,与类型没有半毛钱的关系。
static是静态,实际上是开辟数据公用区,也就是说,如果你见到static,那么所有的都会引用同一地址的数据。而这个数据就是所谓的数据公共区。它和引用方式也没有半毛钱的关系。
几个概念混着来,新手新的太实在了!
//////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
首先一点,我不知道你从何处得来的信息,一个类加上static就是传址,不加就是传值,在C#中没有这样概念。
其次一点,我认为我所说的例子只是能让你暂时理解,但例子并不是真正的贴切。
第三,如果你真能理解,那么你以上的全部问题不是问题!说我没有回答问题,这话说得。。。。
第四,正如五楼所说,值类型是在栈中,而引用类型是堆中,但类的值是在堆栈中,也就是类的值未必全部都是堆中。
如果真的再去给你解释堆栈你未必会懂,你还以为是汇编中的栈啊?问题是汇编中有堆这个概念吗?而且对于堆和栈只是一种结构,是.net运行的基础,并不属于C#。我可以告诉你,两者概念是相同的,但使用方式与所存的内容全部两码事。
第五,如果你真的认为我没有回答问题,你可以只当我发广告,但以后绝不会借你的地儿发广告。
最后,其实个人认为你完全没有必要了解他们在内存中是如何存储的。只有在使用或是做一些IL时才会对这些东西弄的很清楚。而IL却是一种中间语言,学其中一门的C#完全没有必要懂的。不是懂汇编么--那么就是牛人了,IL也算是一种汇编,自己去看看吧!
首选结构体是一个值类型,而类是一个引用类型。
从你的后几句的补充上来说,你还没有型清楚什么是引用类型,什么是值类型。字与传值引用,传址引用是两码事,不要弄一块了!
所以的值类型与引用类型上,我这样给你说一下,看你是否能明白。
值类型的内存单元里是值,而引用类型单元里边是地址,地址指向了值。
比如int是值类型,int
s
=5;
s这个内存单元中就是5,不是地址指针。
而类则是一种引用类型!类中的并不是实际的值,而是一些指针指向了真正的值。
所以值类型就是反映的直接的数据。如:
struct
M(int,int)
这个结构就是直接的值类型,它在内存中的表现是,除了结果体说明,就占两个int空间,用第一个空间里的数做第一个数值,第二个空间的数就是第一个数值。这就是结构体,也就是值类型。
值类型与引用类型说是类型。
传值引用,与址引用说的是引用方式。我给你的参数是一个值,你就按这个类计算去。如果我给的是地址,你计算时直接用的是地址。
在C#中没有传址,而是直接使用的ref参数与out参数将对象直接传入的。
传址引用与传值引用是两种不同的引用方式,与类型没有半毛钱的关系。
static是静态,实际上是开辟数据公用区,也就是说,如果你见到static,那么所有的都会引用同一地址的数据。而这个数据就是所谓的数据公共区。它和引用方式也没有半毛钱的关系。
几个概念混着来,新手新的太实在了!
//////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
首先一点,我不知道你从何处得来的信息,一个类加上static就是传址,不加就是传值,在C#中没有这样概念。
其次一点,我认为我所说的例子只是能让你暂时理解,但例子并不是真正的贴切。
第三,如果你真能理解,那么你以上的全部问题不是问题!说我没有回答问题,这话说得。。。。
第四,正如五楼所说,值类型是在栈中,而引用类型是堆中,但类的值是在堆栈中,也就是类的值未必全部都是堆中。
如果真的再去给你解释堆栈你未必会懂,你还以为是汇编中的栈啊?问题是汇编中有堆这个概念吗?而且对于堆和栈只是一种结构,是.net运行的基础,并不属于C#。我可以告诉你,两者概念是相同的,但使用方式与所存的内容全部两码事。
第五,如果你真的认为我没有回答问题,你可以只当我发广告,但以后绝不会借你的地儿发广告。
最后,其实个人认为你完全没有必要了解他们在内存中是如何存储的。只有在使用或是做一些IL时才会对这些东西弄的很清楚。而IL却是一种中间语言,学其中一门的C#完全没有必要懂的。不是懂汇编么--那么就是牛人了,IL也算是一种汇编,自己去看看吧!
已赞过
已踩过<
评论
收起
你对这个回答的评价是?
展开全部
结构体里没有构造函数,构造函数是用来实力化类的对象的。
类是反映现实事物的一种抽象,而结构体的作用只是一种包含了具体不同类别数据的一种包装,结构体不具备类的继承多态特性
类是反映现实事物的一种抽象,而结构体的作用只是一种包含了具体不同类别数据的一种包装,结构体不具备类的继承多态特性
已赞过
已踩过<
评论
收起
你对这个回答的评价是?
推荐律师服务:
若未解决您的问题,请您详细描述您的问题,通过百度律临进行免费专业咨询