0601-0601-0601-0601-0601-0601-0601-0601-0601-0601-0601-0601-0601-0601-0601-0601-0601-0601-0601-0601-0601-0601-
一、static
1、用于修饰成员(成员变量 或 成员方法)
2、被修饰的成员有如下特点:
(1)、随着类的加载而加载
(2)、优先于对象存在
(3)、被所有的类所共享
(4)、可以直接被类名调用
3、使用注意:
(1)、静态方法只能访问静态成员(非静态方法既可以访问静态方法,也可以访问非静态方法)
(2)、静态方法中不可以写this\super关键字(因为静态优先于对象存在)
(3)、主函数是静态的
二、方法区:也称为 数据区、共享区,用于存放【方法】和【静态变量】
三、【实例变量】和【类变量】的区别:
1、存放位置
(1)、类变量随着类加载而存放在方法区中
(2)、实例变量随着对象的建立而存放在堆内存中
2、声明周期
(1)、类变量随着类的消失而消失
(2)、实例变量随着对象的消失而消失
0602-0602-0602-0602-0602-0602-0602-0602-
public static void main(String[] args)
public:表示该函数的访问权限是最大的
static:该函数随着类的加载已经存在
void:该函数没有具体的返回值
main:不是关键字,是一个特殊的单词,可以被jvm所识别
String[] args:参数的数据类型是数组,数组内部的元素是String类型的,
主函数是固定格式的,可以被JVM识别
0603-0603-0603-0603-0603-0603-0603-0603-
1、何时定义静态变量?
当对象中出现共享数据时,该数据被静态所修饰。
(对象中的特有数据要定义成非静态的,存在于堆内存中)
2、何时定义静态函数?
当该函数内部不会访问非静态数据(对象特有的数据)时,那么该功能可以定义称为静态的。
0604-0604-0604-0604-0604-0604-0604-0604-
1、如果多个方法中含有相同的代码,那么就可以把这些相同的代码抽离出来封装到一个方法中
当需要这些代码时,直接调用这个方法就可以了。
2、当多个类中都需要某个方法时,可以把这个方法提取出来,封装到到一个类(我们称这个类为工具类)中,
需要用这个方法的功能时,调用这个类中的方法即可。
3、当一个类内部有用到另外一个类的时候,系统会先找被用到的类的.class文件,
如果没有.class文件,那么就去找.java文件,让.java文件生成.class文件;
如果也没有.java文件,那么就会报错!!!
class ArrayToolDemo0604{
public static void main(String[] args){
int[] arr={2,5,1,3,6,9,8};
int max=ArrayTool0604.getMax(arr);
System.out.println("max="+max);
ArrayTool0604.printArray(arr);
ArrayTool0604.bubbleSort(arr);
ArrayTool0604.printArray(arr);
}
}
class ArrayTool0604{
//2、将方法都静态以后,可以方便的使用。但是该类还是可以被其他程序建立对象的
//为了更加严谨,强制该类不可以被建立对象,此时,可以通过构造函数私有化来完成。
//
private ArrayTool0604(){};
public static int getMax(int[] arr){
int max=0;
for(int i=0;i<arr.length;i++){
if(arr[i]>arr[max]){
max=i;
}
}
return arr[max];
}
//1、如果程序中不需要建立对象,我们可以使用类名来调用方法,即把类中的所有的方法都定义为static的
//这样,操作会更加方便。
public static int getMin(int[] arr){
int min=0;
for(int i=0;i<arr.length;i++){
if(arr[i]<arr[min]){
min=i;
}
}
return arr[min];
}
public static void selectSort(int[] arr){
for(int i=0;i<arr.length-1;i++){
for(int j=i+1;j<arr.length;j++){
if(arr[i]>arr[j]){
swap(arr,i,j);
}
}
}
}
public static void bubbleSort(int[] arr){
for(int i=0;i<arr.length-1;i++){
for(int j=0;j<arr.length-i-1;j++){
if(arr[j]>arr[j+1]){
swap(arr,j,j+1);
}
}
}
}
private static void swap(int[] arr,int a,int b){
int temp=arr[a];
arr[a]=arr[b];
arr[b]=temp;
}
public static void printArray(int[] arr){
System.out.print("[");
for(int i=0;i<arr.length;i++){
if(i!=arr.length-1){
System.out.print(arr[i]+",");
}else{
System.out.println(arr[i]+"]");
}
}
}
}
0606-0606-0606-0606-0606-0606-0606-0606-
当类中的内容被用到时,类会被加载,类加载之前会先执行静态语句块。
/*
static代码块
1、格式:
static{
静态代码块中要执行的内容;
}
2、特点:
完成类加载时执行,且只执行一次,优于主函数执行,优于构造代码块执行。
*/
//【静态代码块】:给类进行初始化,只可以访问静态属性
//【构造代码块】:给对象进行初始化,可以访问非静态属性。
//【构造函数】:给对应的对象进行初始化
class StaticCode{
static{
System.out.println("a");
}
public static void show(){
System.out.println("show run.........");
}
}
class StaticCodeDemo0606{
static{
System.out.println("b");
}
public static void main(String[] args){
//StaticCode sc=new StaticCode();
//sc.show();
//StaticCode.show();
StaticCode s=null;
s.show();
}
static{
System.out.println("c");
}
}
********************************************
/*
构造代码块
{
}
*/
class StaticCodeDemo0606{
public static void main(String[] args){
new StaticCode(4); //b d c
}
}
class StaticCode{
public StaticCode(){
System.out.println("a");
}
static{
System.out.println("b");
}
{
System.out.println("d");
}
public StaticCode(int s){
System.out.println("c");
}
public static void show(){
System.out.println("show run.........");
}
}
0607-0607-0607-0607-0607-0607-0607-0607-
Person p=new Person("zhangSan",20);
执行完上面这句话,系统都做了哪些事情?
1、因为new用到了Person.class,所以会先找到Person.class文件并加载到内存中。
2、执行该类的static代码块,如果有的话,给Person.class类进行初始化。
3、在堆内存中开辟内存空间,分配内存地址。
4、在堆内存中建立对象的特有属性,并进行属性的默认初始化
5、对属性进行显示初始化
6、对对象进行构造代码块初始化
7、对对象进行相应的构造函数初始化
8、将内存地址赋给栈内存中的p变量
0609-0609-0609-0609-0609-0609-0609-0609-
单例模式:解决类在内存中只有一个对象的问题。
1、为了避免多个程序生成多个对象,应该进制其他程序通过new产生对象。
2、为了让其他程序能得到一个对象,应该在本类中自定义一个对象。
3、为了让其他程序能访问该对象,应该提供一些访问方式。
4、调用一个类的内部的方法有两种方式:
一种是通过对象来调用,另一种是通过类名来调用(被调用的方法必须得被static 修饰)
由于构造方法已经私有化,不能生成对象了。
因此,若想调用方法,只能通过类名调用,要想通过类名调用方法,被调用的方法必须得被static修饰。
5、由于静态方法不能访问非静态属性,为了访问非静态属性Single s,Single s的修饰符应该是static
对于对象该怎么描述,还那样描述。
当需要保证对象在内存中唯一时,加上以上的操作即可。
class Single{
private String name;
public void setName(String name){
this.name=name;
}
public String getName(){
return this.name;
}
//1
private Single(){};
//2
private static Single s=new Single();
//3
public static Single getInstance(){
//5
return s;
}
}
class SingleDemo0609{
public static void main(String[] args){
//4
Single s1=Single.getInstance();
Single s2=Single.getInstance();
s1.setName("liSi");
System.out.println(s2.getName());
}
}
0610-0610-0610-0610-0610-0610-0610-0610-
/*
这个是先初始化对象,称为【饿汉式】===》开发时,多用此种方式。因为可以保证线程安全!
Single类进内存时,就创建了对象。
class Single{
private Single(){};
private static Single s=new Single();
public static Single getSingle(){
return s;
}
}
*/
class Single{
//方法被调用时,才生成对象,这叫做对象的延时加载。也称为【懒汉式】
//Single类进内存时,对象还没有存在,只有调用getSingle()方法时,才建立对象。
private Single(){};
private static Single s=null;
public static Single getSingle(){
if(s==null){
//为了保证线程安全而采取的措施
synchronized(Single.class){
if(s==null){
s=new Single();
}
}
}
return s;
}
}
public class SingleDemo0610{
public static void main(String[] args){
}
}
黑马程序员_07_static_main_工具类_static代码块_单例模式
最新推荐文章于 2023-02-10 14:13:57 发布