java编程思想 初始化_《java编程思想》_第五章_初始化与清理

初始化和清理是涉及安全的两个问题,java中采用了构造器,并额外提供了“垃圾回收器”,对于不再使用的内存资源,垃圾回收器能自动将其释放。

一、用构造器确保初始化

java中,通过提供构造器,类的设计者可以确保每个对象都会得到初始化。创建对象时,如果其类具有构造器,java就会在用户有能力操作对象之前自动调用相应的构造器,从而保证了初始化的进行。考虑到在初始化期间要自动调用构造器,所以构造器与类的名称必须相同。public class IfElse {

public static void main(String[] args){

new Test();//在创建对象时,会为对象分配存储空间,并调用相应的构造器。

}

}

class Test{

Test(){

System.out.println("this is test");

}

}

运行结果:this is test

不接受任何参数的构造器叫做默认构造器(无参构造器),构造器也能带有形式参数,以便指定如何创建对象。public class IfElse {

public static void main(String[] args){

new Test(5);

}

}

class Test{

Test(int i){

System.out.println("this is test"+i);

}

}

运行结果:this is test5

从概念上讲,“初始化”与“创建”是彼此独立的,然而在java中,“初始化”与“创建”捆绑在一起,两者不能分离。

二、方法重载

1.区分重载方法

重载的方法具有相同的名字,但是每个重载的方法都必须有一个独一无二的参数列表,甚至参数顺序的不同也足以区分两个方法,不过一般情况下别这么做,这会使代码难以维护。

2.涉及基本类型的重载

基本类型能从一个“较小”的类型自动提升为一个“较大”的类型,此过程一旦涉及到重载,可能会造成一些混淆。如果传入的数据类型(实际参数类型),小于方法中声明的形式参数类型,实际数据类型就会被提升。char型略有不同,如果无法找到刚好接受char参数的方法,就会把char直接提升至int。如果传入的实际参数类型大于方法中声明的参数类型,就要通过类型转化做窄化转换,否则编译器会报错。

三、默认构造器

如果写的类中没有构造器,则编译器会自动帮你创建一个默认的构造器。但是如果已经定义了一个构造器(无论是否有参数),编译器就不会帮你自动创建默认构造器。

四、this关键字

1.在构造器中调用构造器

可能为一个类写了多个构造器,有时可能会想在一个构造器中调用另一个构造器,以免重复代码,可以用this关键字做到。通常写this关键字的时候,都是指“这个对象”或者“当前对象”,而且它本身表示对当前对象的引用。

public class Flower {

int petalCount = 0;

String s = "initial value";

Flower(int petals){

petalCount = petals;

System.out.println("int arg only,petalCount = "+petalCount);

}

Flower(String ss){

System.out.println("String arg only,s = "+s);

s = ss;

}

Flower(String s,int petals) {

this(petals);

//this(s);此处编译器会报错

this.s = s;

System.out.println("String & int arg");

}

Flower() {

this("hi",47);

System.out.println("no args");

}

public static void main(String args[]){

Flower x = new Flower();

}

}

运行结果:int arg only,petalCount = 47

String & int arg

no args

在有两个参数的构造方法中,试图调用两次构造方法,但是编译器报错。这表明,尽管可以用this调用一个构造器,但却不能调用两个,此外,必须将构造器置于最初始处,否则编译器会报错。

五、清理:终结处理和垃圾回收

java有垃圾回收器负责回收无用对象占据的内存资源,但也有特殊情况:假定你的对象(并非使用new关键字)获得了一块“特殊”的内存区域,由于垃圾回收器只知道释放那些经由new分配的内存,所以它不知道该如何释放该对象的这块“特殊”内存。为了应对这种情况,java允许在类中定义一个名为finalize()的方法。它的工作原理“假定”是这样的:一旦垃圾回收器准备好释放对象占用的存储空间,将首先调用其finalize()方法,并且在下一次垃圾回收动作发生时,才会真正回收对象占用的内存。要记住以下三点:

(1)对象可能不被垃圾回收

(2)垃圾回收不等于“析构”

(3)垃圾回收只与内存有关

1.垃圾回收器如何工作

在java虚拟机中,堆的实现像是一个传送带,每分配一个新对象,它就往前移动一格。这意味着对象存储空间分配的速度非常快,java的“堆指针"只是简单地移动到尚未分配的区域。但实际情况未必像传送带那样,因此,高效率的垃圾回收依赖于垃圾回收器的介入。当它工作时,将一面回收空间,一面使堆中的对象紧凑排列,这样,”堆指针“就可以很容易地移动到更靠近传送带的开始处。通过垃圾回收器对对象的重新排列,实现了一种高速的,有无限空间可以分配的堆模型。

垃圾回收机制了解:

(1)引用记数:简单,但速度很慢。每个对象都含有一个引用计数器,当有引用连接至对象时,引用记数加1,当引用离开作用域或被置于null时,引用记数减1。这个方法有个缺陷,如果对象之间循环引用,可能会出现”对象应该被回收,但引用记数却不为0“的情况。对于垃圾回收器而言,定位这样的交互自引用的对象组所需工作量极大。引用记数常用来说明垃圾收集的工作方式,但似乎从未被应用于任何一种虚拟机。

(2)自适应:java虚拟机采用自适应的垃圾回收技术,停止-复制:先暂停程序,将所有存活的对象复制到另一个堆中,没有被复制的即为垃圾;标记-清扫:遍历所有引用,进而找出所有存活的对象,当没有引用时,变给对象标记,这个过程中不会有任何清理操作。在java虚拟机运行过程中,根据堆空间的对象情况,在以上两种状态切换,以达到垃圾回收。

六、成员初始化

java尽力保证,所有的变量在使用前都能得到恰当的初始化,对于方法的局部变量,java以编译时错误的形式来贯彻这种保证。void f(){

int i;

i++;

}

以上代码编译期会报错变量没有初始化。但是对于类的数据成员,情况有所不同,类的每个基本数据成员保证都会有一个初始值。即使代码没有给出,编译器也会自动赋初值。

七、构造器初始化

1.初始化顺序

在类的内部,变量定义的先后顺序决定了初始化的顺序。即使变量定义散布于方法定义之间,它们仍然会在任何方法(包括构造器)被调用之前得到初始化。class Window{

Window(int marker) {

System.out.println("window("+marker+")");

}

}

class House{

Window w1 = new Window(1);

House(){

System.out.println("House()");

w3 = new Window(33);

}

Window w2 = new Window(2);

void f(){

System.out.println("f()");

}

Window w3 = new Window(3);

}

public class OrderOfInitialization {

public static void main(String[] args){

House h = new House();

h.f();

}

}

运行结果:window(1)

window(2)

window(3)

House()

window(33)

f()

在House类中,故意把几个window对象散布在各处,以证明它们全都会在调用构造器或其他方法之前得到初始化。

2.静态数据的初始化

无论创建多少个对象,静态数据都只占一份存储区域。static关键字不能应用于局部变量,因此它只能作用于域。 初始化的顺序是先静态对象(如果之前并未被初始化),而后是非静态对象。

对象的创建过程,假设有个名为Dog的类:

(1)当首次创建类型为Dog的对象时,java解释器查找类路径,定位Dog.class文件

(2)载入Dog.class,有关静态初始化的所有动作都会被执行。因此,静态初始化只在Class对象首次加载的时候进行一次。

(3)当用new Dog()创建对象时,首先将在堆上为Dog对象分配足够的存储空间。

(4)这块存储空间会被清零,这就自动地将Dog对象中的所有基本类型数据都设置成了默认值,而引用则被置为null。

(5)执行所有出现于字段定义处的初始化动作。

(6)执行构造器。

八、数组初始化

数组只是相同类型的,用一个标识符名称封装到一起的一个对象序列或者基本类型数据序列。

可变参数:String[] args的写法可以写为String...args。有了可变参数,就不用显示地编写数组语法了,当指定参数时,编译器会去填充数组,但是如果传递的本来就是数组,编译器就不会再执行任何转换。因此,如果你有一组事物,可以把它们当作列表传递,而如果你已经有了一个数组,该方法可以把它们当作可变参数列表来接受。将0个参数传递给可变参数列表依旧是可行的。

九、枚举类型

java SE5中添加了一个看似很小的特性,即enum关键字,它使得我们在需要群组并使用枚举类型集时,可以很方便地处理。enum Simple {

NOT,MILD,MEDIUM,HOT

}

public class SimpleEnumUse{

public static void main(String[] args){

Simple howHot = Simple.MEDIUM;

System.out.println(howHot);

}

}

运行结果:MEDIUM

enum有一个特别实用的特性,即它可以在switch语句内使用。

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/news/272768.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

OkHttp 上手

OkHttp 上手 优点 快、节省带宽。支持 HTTP/2 和 SPDY。HTTP/2 和 SPDY 允许对同一个主机的所有请求,使用一个 socket。如果不支持 SPDY 的话,可以用连接池减少请求等待时间。GZIP 缩小传输大小。缓存响应(response ca…

关于Net开发中一些SQLServer性能优化的建议

一、 ExecuteNonQuery和ExecuteScalar 对数据的更新不需要返回结果集,建议使用ExecuteNonQuery。由于不返回结果集可省掉网络数据传输。它仅仅返回受影响的行数。如果只需更新数据用ExecuteNonQuery性能的开销比较小。 ExecuteScalar它只返回结果集中第一行的第一列…

jstl mysql_java – jsp jstl sql与mysql中的奇怪行为

在mysql中我有一个存储过程,其中包含一个sql:select firstname as i_firstname , lastname as i_lastname from roleuserwhere user_id uid ;我使用jstl代码来获取值: –call sp_select_username(?);${rows.i_firstname} ${rows.i_lastname}但是这个代…

C# 哈希表(Hashtable)用法笔记

一、什么是Hashtable?Hashtable 类代表了一系列基于键的哈希代码组织起来的键/值对。它使用键来访问集合中的元素。当您使用键访问元素时,则使用哈希表,而且您可以识别一个有用的键值。哈希表中的每一项都有一个键/值对。键用于访问集合中的项…

转: Div与table的区别

1&#xff1a;速度和加载方式方面的区别 div 和 table 的差异不是速度&#xff0c;而是加载方式&#xff0c;速度只能是指网络速度&#xff0c;如果速度足够快&#xff0c;是没有差异的&#xff1a; div 的加载方式是即读即加载&#xff0c;遇到 <div> 没有遇到 </div…

你的工作是为了你自己!

1、无论为谁打工&#xff0c;要为自己学东西&#xff0c;客观为公司创造价值。我自己当年&#xff0c;无论我在方正给国内企业工作&#xff0c;还是我在雅虎给外国人工作&#xff0c;我都跟别人最大的不一样&#xff0c;我从来不觉得我在给他们打工&#xff0c;我真的可能是很有…

java 无法注入service_SpringBoot集成shiro,MyRealm中无法@Autowired注入Service的问题

网上说了很多诸如是Spring加载顺序&#xff0c;shiroFilter在Spring自动装配bean之前的问题&#xff0c;其实也有可能忽略如下低级错误。在ShiroConfiguration中要使用Bean在ApplicationContext注入MyRealm&#xff0c;不能直接new对象。道理和Controller中调用Service一样&…

python之函数用法startswith()

# -*- coding: utf-8 -*- #python 27 #xiaodeng #python之函数用法startswith() #http://www.runoob.com/python/att-string-startswith.html#startswith() #说明&#xff1a;返回布尔值,用于检查字符串是否是以指定子字符串开头&#xff0c;如果是则返回 True&#xff0c;否则…

别去取悦,心里没你的人

鞋子不合适不必硬塞&#xff0c;否则磨了自己的脚&#xff1b;不必讨好心里没你的人&#xff0c;不在乎你的人&#xff0c;你付出再多&#xff0c;也打动不了他。讨好心里没你的人&#xff0c;会让自己很累很累&#xff1b;总是迁就他&#xff0c;总是围着他转&#xff0c;最后…

tensorflow java 加速_Tensorflow使用GPU加速

测试faster-rcnn时&#xff0c;cpu计算速度较慢&#xff0c;调整代码改为gpu加速运算将 with tf.Session() as sess: 替换为1 gpu_options tf.GPUOptions(per_process_gpu_memory_fraction0.9)2 with tf.Session(configtf.ConfigProto(gpu_optionsgpu_options,log_device_plac…

Install OpenStack Kilo Dashboard wiht Nginx + uWSGI On RHEL7.1

一、安装Horizon、Nginx、uWSGI yum install -y uwsgi-plugin-python openstack-dashboard uwsgi nginx 二、配置uWSGI cat >/etc/uwsgi.ini <<EOF [uwsgi] plugins python master true processes 10 threads 2 chmod-socket 666socket 127.0.0.1:9000 pidfile …

C#枚举类型的笔记

一、枚举类型的概念枚举类型声明为一组相关的符号常数定义了一个类型名称。枚举用于"多项选择"场合&#xff0c;就是程序运行时从编译时已经设定的固定数目的“选择”中做出决定。枚举类型&#xff08;也称为枚举&#xff09;为定义一组可以赋给变量的命名整数常量提…

java动态打印_JFreeChart学习(三)——动态打印java内存使用情况

JFreeChart动态打印java内存使用情况import java.awt.BasicStroke;import java.awt.BorderLayout;import java.awt.Color;import java.awt.Font;import java.awt.event.ActionEvent;import java.awt.event.ActionListener;import java.awt.event.WindowAdapter;import java.awt…

WPF中StringToImage和BoolToImage简单用法

在WPF的绑定控件操作中&#xff0c;经常会通过bool值或者某些特定的string值做出相应动作。但UI层控件的很多属性对应的都不是Bool值或者对应的只是固定的String值。 这个时候有两方法解决该问题。 1.是在后台cs中做出比较判断&#xff0c;然后根据相应结果传达UI层做出相应动作…

【必备】jQuery性能优化的38个建议

一、注意定义jQuery变量的时候添加var关键字这个不仅仅是jQuery&#xff0c;所有javascript开发过程中&#xff0c;都需要注意&#xff0c;请一定不要定义成如下&#xff1a;$loading $(#loading); //这个是全局定义&#xff0c;不知道哪里位置倒霉引用了相同的变量名&#xf…

java中策略设计模式_Java中的设计模式(五):策略模式

策略设计模式是行为设计模式之一。当我们为特定任务使用多个算法时&#xff0c;使用策略模式&#xff0c;客户端决定在运行时使用的实际实现。策略模式的最佳示例之一是Collections.sort()采用Comparator参数的方法。基于Comparator接口的不同实现&#xff0c;对象将以不同的方…

isset函数

isset (PHP 4, PHP 5) isset — 检测变量是否设置 检测变量是否设置&#xff0c;并且不是 NULL。 如果 var 存在并且值不是 NULL 则返回 TRUE&#xff0c;否则返回 FALSE。 $a "test"; $b "anothertest";var_dump(isset($a)); // TRUE var_dump(i…

SQLl中的left join、right join、inner join详解

left join(左联接) 返回包括左表中的所有记录和右表中联结字段相等的记录right join(右联接) 返回包括右表中的所有记录和左表中联结字段相等的记录inner join(等值连接) 只返回两个表中联结字段相等的行举例如下&#xff1a;--------------------------------------------表A记…

afudos备份bios不动_bios刷坏后的两种解决方法

通常主板新的BIOS可以修正旧版中BIOS的一些BUG&#xff0c;纠正对某些硬件和软件的兼容问题&#xff0c;添加新硬件的支持等等&#xff0c;所以有时我们需要刷新BIOS。但刷新主板BIOS实际上是存在一定风险的&#xff0c;虽然现在各主板厂商都推出了在Windows下刷新BIOS的软件&a…

光学基础知识:白光、颜色混合、RGB、色彩空间

1665年&#xff0c;牛顿(Isaac Newton)进行了太阳光实验&#xff0c;让太阳光通过窗板的小圆孔照射在玻璃三角棱镜上&#xff0c;光束在棱镜中折射后&#xff0c;扩散为一个连续的彩虹颜色带&#xff0c;牛顿称之为光谱&#xff0c;表示连续的可见光谱。而可见光谱只是所有电磁…