一、封装
基本概念
封装思想:隐藏对象的属性和方法细节且对设置或读取类中的属性进行限制,防止他人随意操作。
封装概念:在设计一个类时,对类的属性和方法进行私有化限制。也就是用private、protected、public等关键字修饰。用户想要访问私有属性,需要通过public的setter和getter方法或者其他方法来操作。
生活现象:大家都使用过网上购物,在某电商网站购买商品时需要填写购买种类和数量,我们只能填写正确的数量,如果你输入-1,或者你输入的值大于店家的库存,那显然是不可以的。而且我们也不可以操作商品的单价。
这里就是对购买商品的属性的封装,在购买数量上,对它的访问进行了某些限制,要求数量大于0且小于库存。而对于商品单价,压根就没有给出访问的公共方法,不然大家都可以修改单价就乱套了。
访问级别关键字
修饰词 | 本类 | 同包中的类 | 子类(继承类) | 其他类 |
---|---|---|---|---|
private | √ | |||
default(默认) | √ | √ | ||
protected | √ | √ | √ | |
public | √ | √ | √ | √ |
强调:对于java中的类(不是内部类)来说,其访问权限只有public和无(包访问权限)两种,没有protected和private。
java中的包
正确理解封装的概念就要先理解java中包的概念。
概念:
java中使用包来组织程序,因为开发一个项目由N多人来完成,有可能出现类名相同的情况。这样上传到服务器就无法成功或者上传成功也会将原来服务器上同名的文件覆盖掉。包可以有效的解决类名冲突及更好的管理类。
包的声明:通过package关键字创建,语句格式:package com.Login.demo 包名通常是网络的倒置域名,且声明包的语句必须是程序的第一句非注释性代码(前面可以有注释,但不能有其他语句),有且仅有一条。
package exercise;
public class Demo1 {
public static void main(String[] args) {
System.out.println("Hello World!!!");
}
}
在idea上写这么一段代码,我们项目的输出目录上就会出现Demo1.java的文件,如果继续用idea的话,它会帮助我们省去编译运行的操作,直接在控制台上输出。但对于想使用手动编译的同学。
在命令行先进入文件所在目录(到包的内部),javac Demo1.java 编译生成字节码文件,这样目录中就会出现Demo1.class , 再用java Demo1运行,然后你就发现报错了
错误: 找不到或无法加载主类 exercise.Interfac
原因: java.lang.ClassNotFoundException: exercise.Demo1
原因是,我们必须回到包所在的目录(上一级目录 cd …/),并且加上类名exercise
java exercise.Demo1
至此大功告成
原理:
打包前的类名 Demo1,打包后的类名(带有包名的类名)exercise.Demo1
并且要回到包所在的目录才能找到
导包:
关键字:import
- 导入某个包中的指定类
- 导入某个包中的所有类
import java.util.*
import java.util.Scanner
//这两种语句性能相同,使用*时程序也是在执行时自动加载需要的类
静态导入
在JDK1.5以后加入了静态导入,如果一个类中所有的属性和方法都是静态的,就可以使用静态导入。优势是,在调用静态方法时可以省略类名直接调用
package staticdemo;
public class Calc {
public static int number = 20;
public static int count = 10;
public static int add(){
return number + count;
}
}
package cn.sxt.demo;
import static staticdemo.Calc.*; //静态导入
import static java.lang.Math.*;
public class TestPackage {
Public static void main(String[] args) {
System.out.println(add()); //调用自定义类中的add()方法
System.out.println(random());
}
}
到这里大家对包的理解就更深一层了。
其他操作
- 包将类封装到了不同目录中
- 同一个包中的类,可以直接用类名访问
- 不同包中的类,可以使用包名.类名的形式来访问
- 不同包中的类,还可以用关键字import导入所在的包,这样就可以直接用类名访问
常用包
在Java的JDK中提供了大量的实用类,通常称为API,这些类按功能 不同,分别被放到了不同的包中,供编程使用;常用的包有6个。
① Java.lang 包含java语言的核心类
② Java.awt 包含抽象窗口工具集
③ Java.swing 包含用于管理可视化组件的类
④ Java.net 包含与网络操作相关的类
⑤ Java.io 包含提供多种输入、输出的类
⑥ Java.util 包含一些使用工具类,如集合类等
其中java.lang是编译器中自动添加的,awt和swing是有关于GUI图形界面开发所需要的
this关键字
**概念:**指代当前对象,存储的是当前对象的内存地址
public class Person {
public Person(){
System.out.println("this="+this);
}
public static void main(String[] args){
Person person = new Person();
System.out.println("person = "+person);
}
}
this=exercise.Person@1d81eb93
person = exercise.Person@1d81eb93
this的作用:
-
可以访问本类的属性:this.属性名。this可以省略
-
可以调用本类的方法:this.方法名()。this可以省略
-
可以调用本类的构造方法:(必须是构造方法中的第一句代码)
this.():调用本类的无参构造方法
this(实参值):调用本类的带参构造方法。
-
当局部变量与成员变量名称相同时,使用this代表成员变量
public class Person { private String name; private int age; //公有的赋值方法 public void setName(String name) { this.name = name; } //无参构造方法 public Person(){ } public Person(String name){ //调用本类的无参构造方法,放在构造方法的第一非注释句 this(); this.name = name; } public Person(String name,int age){ //调用本类的带参构造方法 this(name); this.age = age; } public void show(){ System.out.println("姓名:使用this="+this.name); System.out.println("姓名:省略this="+name); } public void intro(){ System.out.println("调用show方法,使用this"); this.show(); System.out.println("调用show方法,省略this"); show(); } public static void main(String[] args){ Person person = new Person(); System.out.println("person = "+person); } }
static关键字
概念:
static主要用来修饰类,类的属性,类的方法,代码块。方便在没有创建对象的情况下调用。
作用(我一定不会告诉你有五点的)
-
修饰成员变量,修饰后称之为静态变量或者类变量
private String name; private int age; public static String city; //带参的构造方法 public Student(String name, int age){ this.name = name; this.age = age; } //编写show方法 public void show(){ System.out.println("姓名:"+name+"\t年龄:"+age+"\t城市:"+city); } public static void main(String[] args) { //因为city是静态变量,是属于类的,赋值一次所有对象都拥有了 Student.city = "太原"; Student student1 = new Student("李国瑞",18); Student student2 = new Student("孙伟峰",18); student1.show(); student2.show(); }
[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-aPMA2KbS-1586181578269)(E:\李国瑞\云顶书院\博客\static.png)]
-
修饰成员方法,修饰后称之为静态方法或者类方法
这里说一下成员方法的优劣:
好处是成员方法在类加载时就被加载到内存,因此可以直接使用类名调用。对于经常使用的或者需要初始化加载时要用。
坏处是初始化加载比较占用内存,不经常使用的方法不建议用static修饰
注意
类方法不允许使用非static的属性或者方法,因为静态方法加载到内存时还没有创建对象,而实例变量和实例方法是依赖于对象的。
-
修饰代码块,修饰后称之为静态代码块
-
修饰内部类,修饰后称之为静态内部类
注意:普通类是不允许声明为静态的,只有内部类才可以。
- 静态导包:上文详细介绍
代码块
普通代码块(猜猜结果)
import static java.lang.System.out;
public class TestStaticImport {
public static void main(String[] args) {
{
int i = 10;
out.println("我是普通代码块");
}
for(int i=0;i<10;i++){
out.println("i="+i);
}
}
}
构造代码块(在类中被定义,且先与构造方法被执行)
import static java.lang.System.out;
public class TestStaticImport {
public TestStaticImport(){
out.println("我是构造方法");
}
//构造代码块,声明再类中
{
out.println("我是构造代码块(我比构造方法先执行)");
}
public static void main(String[] args) {
TestStaticImport block = new TestStaticImport();
}
}
静态代码块
import static java.lang.System.out;
public class TestStaticImport {
public TestStaticImport(){
out.println("我是构造方法");
}
//构造代码块,声明再类中
{
out.println("我是构造代码块(我比构造方法先执行)");
}
//静态代码块
static{
out.println("我是静态代码块,我是比他们两个快,但我只执行一次");
}
public static void main(String[] args) {
TestStaticImport block = new TestStaticImport();
}
}
/*
我是静态代码块,我是比他们两个快,但我只执行一次
我是构造代码块(我比构造方法先执行)
我是构造方法
*/
同步代码块(限于作者水平,感兴趣的同学可以点击链接或者自行百度)
如果文中出现错误,欢迎大家指正或与我联系,大家共同进步