Java和C#中的int和Integer有什么区别?

CodingWithoutComments 237 c# java int integer

当我遇到Joel Spolsky时,我正在阅读更多关于Joel on Software的文章,说明一种特定类型的程序员知道a 和Java/C#(面向对象编程语言)之间的区别.intInteger

那么区别是什么呢?

Matt.. 231

在Java中, 'int'类型是基元,而'Integer'类型是对象.

在C#中, 'int'类型System.Int32value类型相同(即更像java'int').可以将整数(与任何其他值类型一样)装箱("包装")到对象中.


对象和原语之间的差异有些超出了这个问题的范围,但总结如下:

对象提供多态性的工具,通过引用传递(或者更准确地说具有通过值传递的引用),并从堆中分配.相反,基元是不可变类型,它们通过值传递并且通常从堆栈中分配.

  • "对象[...]通过引用传递"的陈述令人困惑和错误,IMO.更准确地说"对象引用是按值传递的".(也不总是从栈中分配原语 - 考虑对象中的原始字段......) (61认同)
  • -1.这可以准确地描述Java如何处理这个问题,但对于C#来说,这是完全错误的. (8认同)
  • 为什么要投票?答案是错的.它不适合Java,甚至不适合C#.阅读此内容的人会比以前知道关于该主题的*更少*. (8认同)
  • 对不起,英语不会"通过引用传递内容"和"通过值传递引用"等效语句,也不会在编程语言上下文中具有相同的含义. (6认同)
  • 至少在C#中,int是一个语言关键字,它等同于Int32 CLR(实际上是CTS)类型. (5认同)

cmcculloh.. 146

好吧,在Java中,int是一个原语,而Integer是一个Object.意思是,如果你做了一个新的整数:

Integer i = new Integer(6);

你可以在i上调用一些方法:

String s = i.toString();//sets s the string representation of i

而使用int:

int i = 6;

你不能在它上面调用任何方法,因为它只是一个原始方法.所以:

String s = i.toString();//will not work!!!

会产生错误,因为int不是一个对象.

int是Java中为数不多的原语之一(以及char和其他一些原语).我不是100%肯定,但我认为Integer对象或多或少只有一个int属性和一大堆与该属性交互的方法(例如toString()方法).所以Integer是一种使用int的奇特方式(就像String可能是一种使用一组字符的奇特方式).

我知道Java不是C,但是因为我从未在C中编程,所以这是我能得到答案的最接近的.希望这可以帮助!

整数对象javadoc

整数Ojbect与int原语比较


Chris Jester.. 37

我将添加上面给出的优秀答案,并讨论装箱和拆箱,以及这如何适用于Java(尽管C#也有).我将仅使用Java术语,因为我对此更加自信.

正如所提到的答案,int只是一个数字(称为未装箱的类型),而是Integer一个对象(包含数字,因此是一个盒装类型).在Java而言,这意味着(除了不能够呼吁的方法int),你不能存储int或集合(其他非对象类型List,Map等等).要存储它们,您必须先将它们装入相应的盒装类型中.

Java 5以后有一种称为自动装箱自动拆箱的功能,可以在后台完成装箱/拆箱.比较和对比:Java 5版本:

Deque<Integer> queue;

void add(int n) {
    queue.add(n);
}

int remove() {
    return queue.remove();
}

Java 1.4或更早版本(也没有泛型):

Deque queue;

void add(int n) {
    queue.add(Integer.valueOf(n));
}

int remove() {
    return ((Integer) queue.remove()).intValue();
}

必须注意的是,尽管Java 5版本简洁,但两个版本都生成相同的字节码.因此,尽管自动装箱和自动拆箱非常方便,因为您编写的代码较少,但这些操作确实在幕后发生,运行成本相同,因此您仍需要了解它们的存在.

希望这可以帮助!

  • Deque不在java 1.5或1.4中.它是在1.6中添加的. (2认同)

Lasse Vågsæt.. 28

我会在这里发帖,因为其他一些帖子与C#有些不准确.

正确: int是别名System.Int32.
错误: float不是别名System.Float,但是System.Single

基本上,int是C#编程语言中的保留关键字,并且是System.Int32值类型的别名.

但是,float和Float不一样,因为'' float'' 的正确系统类型是System.Single.有些类似的保留关键字似乎不直接匹配类型名称.

在C#中,除了定义枚举之外,'' int''和'' System.Int32''或任何其他对或关键字/系统类型之间没有区别.使用枚举,您可以指定要使用的存储大小,在这种情况下,您只能使用保留关键字,而不能使用系统运行时类型名称.

更确切地说,int中的值将存储在堆栈中,内存中,或者作为引用的堆对象取决于上下文以及如何使用它.

这个声明在一个方法中:

int i;

根据优化,定义i类型的变量System.Int32,生活在寄存器或堆栈中.类型(结构或类)中的相同声明定义成员字段.方法参数列表中的相同声明定义了一个参数,其存储选项与局部变量相同.(请注意,如果您开始将迭代器方法拉入混合中,则此段落无效,这些是完全不同的野兽)

要获取堆对象,可以使用装箱:

object o = i;

这将创建i堆上内容的盒装副本.在IL中,您可以直接访问堆对象上的方法,但在C#中,您需要将其强制转换为int,这将创建另一个副本.因此,如果不创建新int值的新盒装副本,则无法在C#中轻松更改堆上的对象.(呃,这一段并不容易理解.)


andnil.. 20

关于Java 1.5和autoboxing,在比较Integer对象时会有一个重要的"怪癖".

在Java中,值为-128到127的Integer对象是不可变的(也就是说,对于一个特定的整数值,比如23,所有通过程序实例化的Integer对象,其值为23指向完全相同的对象).

例如,这返回true:

Integer i1 = new Integer(127);
Integer i2 = new Integer(127);
System.out.println(i1 == i2); //  true

虽然这返回false:

Integer i1 = new Integer(128);
Integer i2 = new Integer(128);
System.out.println(i1 == i2); //  false

==按引用进行比较(变量是否指向同一对象).

根据您使用的JVM,此结果可能会有所不同,也可能不会有所不同.Java 1.5的规范自动装箱要求整数(-128到127)总是用同一个包装器对象.

一个办法?=)在比较Integer对象时,应始终使用Integer.equals()方法.

System.out.println(i1.equals(i2)); //  true

更多信息,请访问java.net.例如bexhuff.com

  • 与==相比,使用new运算符创建的对象将始终返回false.Andreas将Integer.valueOf(int)与新的Integer(int)混淆 (3认同)

grom.. 19

在Java中,JVM中有两种基本类型.1)原始类型和2)参考类型.int是基本类型,Integer是类类型(它是一种引用类型).

原始值不与其他原始值共享状态.类型为基本类型的变量始终包含该类型的原始值.

int aNumber = 4;
int anotherNum = aNumber;
aNumber += 6;
System.out.println(anotherNum); // Prints 4

对象是动态创建的类实例或数组.引用值(通常只是引用)是指向这些对象的指针和一个特殊的空引用,它指的是没有对象.可能有许多对同一对象的引用.

Integer aNumber = Integer.valueOf(4);
Integer anotherNumber = aNumber; // anotherNumber references the 
                                 // same object as aNumber

同样在Java中,所有内容都按值传递.对于对象,传递的值是对象的引用.因此java中int和Integer之间的另一个区别是它们在方法调用中的传递方式.例如在

public int add(int a, int b) {
    return a + b;
}
final int two = 2;
int sum = add(1, two);

变量2作为原始整数类型2传递.而在

public int add(Integer a, Integer b) {
    return a.intValue() + b.intValue();
}
final Integer two = Integer.valueOf(2);
int sum = add(Integer.valueOf(1), two);

变量2作为对包含整数值2的对象的引用传递.


@WolfmanDragon:通过引用传递将如下工作:

public void increment(int x) {
  x = x + 1;
}
int a = 1;
increment(a);
// a is now 2

当调用increment时,它将引用(指针)传递给变量a.而增量函数直接修改变量一个.

对于对象类型,它将按如下方式工作:

public void increment(Integer x) {
  x = Integer.valueOf(x.intValue() + 1);
}
Integer a = Integer.valueOf(1);
increment(a);
// a is now 2

你现在看到了区别吗?


huseyint.. 12

在C#中,int是只是一个别名System.Int32,字符串System.String,双对System.Double等...

我个人更喜欢int,string,double等,因为它们不需要using System;声明:)一个愚蠢的理由,我知道......

  • 应该补充一点,C#的int/Int32与*的整数不同*. (2认同)

用户甲.. 9

使用包装类的原因有很多:

  1. 我们得到额外的行为(例如我们可以使用方法)
  2. 我们可以存储空值,而在原语中我们不能
  3. 集合支持存储对象而不是基元.


Wedge.. 8

这已经得到了Java的回答,这是C#答案:

"Integer"不是C#中的有效类型名称,"int"只是System.Int32的别名.此外,与Java(或C++)不同,C#中没有任何特殊的基本类型,C#(包括int)中每个类型的实例都是一个对象.这是一些示范代码:

void DoStuff()
{
    System.Console.WriteLine( SomeMethod((int)5) );
    System.Console.WriteLine( GetTypeName<int>() );
}

string SomeMethod(object someParameter)
{
    return string.Format("Some text {0}", someParameter.ToString());
}

string GetTypeName<T>()
{
    return (typeof (T)).FullName;
}

  • 实际上,在C#Int32中是一个对象.它是一个来自system.object的valuetype结构对象.它与其他值对象的处理方式不同,因为"int"将在Java中. (4认同)
  • 需要说明的是,在C#中,int和System.Int32都不是对象.它们是值类型,CLR与对象的处理方式大不相同. (2认同)

mP... 8

在像Java这样的平台中,ints是基元,Integer而是包含整数字段的对象.重要的区别在于原语总是按值传递,按定义是不可变的.

涉及基元变量的任何操作始终返回新值.另一方面,对象通过引用传递.有人可能会争辩说,对象(AKA引用)的点也是按值传递的,但内容却没有.


用户甲.. 8

int用于声明原始变量

e.g. int i=10;

Integer用于创建Integer类的引用变量

Integer a = new Integer();


J-Alex.. 8

Java的:

int,double,long,byte,float,double,short,boolean,char-图元.用于保存语言支持的基本数据类型.原始类型不是对象层次结构的一部分,它们不继承Object.它可以通过引用传递给方法.

Double,Float,Long,Integer,Short,Byte,Character,和Boolean,是类型包装器,封装在java.lang.所有数值类型包装器都定义了构造函数,这些构造函数允许从给定值构造对象,或者使用该值的字符串表示形式.即使是最简单的计算,使用对象也会增加开销.

从JDK 5开始,Java包含两个非常有用的功能:autoboxing和autounboxing.自动装箱/拆箱大大简化并简化了必须将原始类型转换为对象的代码,反之亦然.

构造函数示例:

Integer(int num)
Integer(String str) throws NumberFormatException
Double(double num)
Double(String str) throws NumberFormatException

装箱/拆箱的示例:

class ManualBoxing {
        public static void main(String args[]) {
        Integer objInt = new Integer(20);  // Manually box the value 20.
        int i = objInt.intValue();  // Manually unbox the value 20
        System.out.println(i + " " + iOb); // displays 20 20
    }
}

自动装箱/自动装箱示例:

class AutoBoxing {
    public static void main(String args[]) {
        Integer objInt = 40; // autobox an int
        int i = objInt ; // auto-unbox
        System.out.println(i + " " + iOb); // displays 40 40
    }
}

PS Herbert Schildt的书作为参考.


Telcontar.. 7

还有一件事我在之前的答案中没有看到:在Java中,原始包装类(如Integer,Double,Float,Boolean ...和String)被认为是不变的,因此当您传递这些类的实例时,调用方法不能以任何方式改变你的数据,在大多数其他类的opositión中,内部数据可以通过其公共方法改变.因此,除了构造函数之外,这个类只有'getter'方法,没有'setter'.

在java程序中,字符串文字存储在堆内存的单独部分中,只存储文字的实例,以节省重用这些实例的内存


Mr.Q.. 7

你之前编程过吗(int)是你可以为变量设置的原始类型之一(就像char,float,...).

但是Integer是一个包装类,你可以使用它来对int变量做一些函数(例如将它转换为字符串,反之亦然,......),但请注意包装类中的方法是静态的,所以你可以使用它们无需创建Integer类的实例.作为回顾:

int x;
Integer y; 

x和y都是int类型的变量,但是y由Integer类包装并且有几个你使用的方法,但是我需要调用Integer包装类的一些函数,你可以简单地完成它.

Integer.toString(x);

但要注意x和y都是corect,但是如果你想将它们用作原始类型,请使用简单形式(用于定义x).


提问时间:

查看次数:

229275 次

最近活跃:

1 年 前