[软件构造] 数据类型和类型检查
java数据
基本数据类型(Primitives) |
对象数据类型(Object Reference Types) |
没有引用,只有值 |
引用与对应的值不相同 |
不可变 |
有的可变,有的不可变 |
保存在栈中,被使用的时候才存在 |
保存在堆中,会被垃圾回收机制回收 |
使用成本低 |
成本高 |
基本数据类型(Primitives):
如int,long,double,boolean,char(首字母小写)
对象数据类型(Object Reference Types)(一般首字母大写)
- Object类是所有类 的基类。所有类默认都继承了 Object类
- 子类与其超类(父类)的关系:
– 从其超类继承可见字段和方法
– 可以覆盖(重写)方法来改变他们的行为 - 一些分散的知识点:
– 一些基本数据类型被封装为对象。如Boolean, Integer, Short, Long, Character, Float, Double。在使用构造collections容器的时候只能使用对象数据类型,但对容器操作的时候可以直接使用基本数据类型(语言会自动进行转换)。
1.如:List list = new ArrayList();
list.add(1);
2.上面list.add(1) 会自动执行list.add(Integer.valueOf(1)),但1不是对象类型,但编译能够通过,自动完成转换,但会降低效率;
– 重载运算符和方法:相同的操作名称用于不同 的数据类型。java不支持重载运算符(除了String的“+”运算(相当于执行 String c = (new StringBuilder(String.valueOf(a))).append(b).toString(); )等少量情况之外),或者说,java已经好了关于数字的运算符
变量类型的确定:
所有变量的类型在编译时(程序运行之前)都是已知的,因此编译器也可以推断出所有表达式的类型。如果a和b声明为int,则编译器断定a + b也是int。事实上,Eclipse环境在写代码的时候执行此操作,因此在编译之前打代码的时候IDE便会报错。但是在像Python这样的动态类型语言中,这种检查会延迟到运行时(程序运行时)。
类型检查:
- 分类:
– 静态检查:在程序运行之前自动发现错误。将操作应用于错误类型的参数会导致错误,静态检查会帮助避免因使用错误类型的操作而导致的错误。一般包括:语法错误、方法的参数个数种类、方法的返回类型等
– 动态:执行代码时会自动发现错误。检查举例:
1.非法参数值。 例如,当y实际为零时,在整数表达式x / y中是错误的
2.超出范围的索引
3.调用空对象的方法
– 无:语言根本无法帮助您找到错误。 你必须自己观察,或者得到错误的答案 - 类型转换,java会进行数据类型转换。基本数据类型的如
double a = 2; // a = 2.0(隐式)
int a = 18.7; // 报错
int a = (int)18.7; // a = 18
对象数据类型的,比如子类型可以转换为父类型,这里不细说了。 - 静态、动态检查对比:
– 静态检查针对类型,与变量 特定值无关的错误,某些变量的值 只有运行时才会知道,动态检查针对由特定值引起的错误。
– 注:double的NaN不是动态检查出来的错误
可变与不可变类型
- 改变变量和改变值的区别:对变量赋值是在改变变 量的指向,指向不同的值;改变可变变量的内容时 ,是在改变变量内部内容的引用。优秀的程序员避免改变变量,容易出问题。因此,我们有不可变类型
- Immutability不变性
– 概念:
1.可变类型:一旦被创建,只代表固定值
2.不可变:可以有改变对象值的方法
– 不变性是一种主要的设计原则
– java提供的final修饰符,保证不变引用,一旦指定引用位置,不可再次指定(final修饰的成员变量在构造方法里赋值),Final关键 字对不可变引用提供了静态检查的支持。注意
1.final class意味着它不能被继承
2.final variable(变量)意味着它始终包含相同的值/引用但不能更改;
3.final method(方法)意味着它不能被子类覆盖;
– 注意:引用不可变,但指向的值却可以是可变的数据类型属于可变类型
Arrays和Collections
- 数组(Arrays):长度固定的序列
- List:可变长度的序列。具体实例化:如ArrayList 、LinkedList。注:1、List是一个接口,不可实例化。2、List的成员必须是对象类型
- Set:零个或多个唯一对象的无序集合,对象不能重复出现。set是抽象接口。具体实例化:HashSet
- Map:键值对,抽象接口。具体实例化:HashMap
- 从Arrays建立list:
Arrays.asList(new String[] { “a”, “b”, “c” }) - collections:
– b、c以及Quene的集合均继承自Collections,使用Collections的时候我们可以限制Collections中包含的对象类型。
– 当添加一个成员时 ,编译器执行静态检查,确保只添加合适类型的成员。 - 迭代器(Iterator):
– 迭代器是一个对象,它遍历一组序列元素并逐个返回元素。遍历时默认调用迭代器。
– 改变序列可能会破坏迭代器。比如迭代的时候不能从序列中remove元素
一些不可变类型
可变类型的不可变包装(Unmodifiable wrappers):List–Collections.unmodifiableList。Set – Collections.unmodifiableSet。Map – Collections.unmodifiableMap
空引用(Null references)
- 对象和数组的引用可以采用特殊值Null,这意味着引用不指向对象。注意:null是Java类型系统中一个不幸的漏洞
- 基本数据类型,不能复制为null。可以为任何非基本数据类型赋值null,编译器在编译时很好地接受此代码。
- 注意:null指的不是“”或者空的array或Collections,非空的collection可以包含null值
- 由于粗心地使用null会导致各种各样的错误,null的含义含糊不清。比如Map.get(key)返 回null可能是key对应的值就是null,或者map中没有此key对应的值,所以建议不要使用null。而且,在参数和返回值中隐式禁止null。
总结
数据类型是编程的基础。java为我们提供了基本数据类型以及对象数据类型。合理的使用它们、了解它们的性质是进一步编程的基础。因此,一定要搞清基本数据类型与对象数据类型的区别,不要弄混了类、引用、对象等概念。
【推荐】国内首个AI IDE,深度理解中文开发场景,立即下载体验Trae
【推荐】编程新体验,更懂你的AI,立即体验豆包MarsCode编程助手
【推荐】抖音旗下AI助手豆包,你的智能百科全书,全免费不限次数
【推荐】轻量又高性能的 SSH 工具 IShell:AI 加持,快人一步
· winform 绘制太阳,地球,月球 运作规律
· 震惊!C++程序真的从main开始吗?99%的程序员都答错了
· AI与.NET技术实操系列(五):向量存储与相似性搜索在 .NET 中的实现
· 超详细:普通电脑也行Windows部署deepseek R1训练数据并当服务器共享给他人
· 【硬核科普】Trae如何「偷看」你的代码?零基础破解AI编程运行原理