java笔记(多线程+包)-第21天

 


包:对类文件进行分类管理。
    给类提供多层命名空间。
    写在程序文件的第一行


    类名的全称的是:包名.类名。
    包也一种封装形式。

    示例1:

1.  package mypack;//包,package首字母小写。

2.   

3.  class PackageDemo{

4.         publicstatic void main(String[] args){

5.             System.out.println("Hello Package!");

6.         }

7.  }

8.   

复制代码

   运行结果:编译通过运行报错。  没有找到这样的类


 

 

    创建mypack文件夹,并且将PackageDemo.class放入其中,然后再次执行。

 


   

    直接java mypack.PackageDemo

运行结果:


 

 

    也可以通过javac命令直接创建mypack文件夹,然后执行。

 


    

 

    示例2:

   DemoA.java

1.  package packa;

2.   

3.  public class DemoA{

4.         publicvoid show(){

5.             System.out.println("demoa show run");

6.         }

7.  }

8.   

复制代码

   PackageDemo.java

1.  package mypack;

2.   

3.  class PackageDemo{

4.         publicstatic void main(String[] args){

5.                  //新创建一个对象packa.DemoA

6.              packa.DemoA d = new packa.DemoA();

7.              d.show();

8.              System.out.println("Hello Package!");

9.         }

10. }

11.  

复制代码

    Cmd命令行输入javac –d. DemoA.java创建生成DemoA.class文件。

运行结果:


    P.S.
    包与包之间的类进行访问,被访问的包中的类必须是public的,被访问的包中的类的方法也必须是public的。

    示例3:
    DemoA.java  

1.  package packa;

2.   

3.  public class DemoA extends packb.DemoB{//A继承B

4.         publicvoid show(){

5.             method();

6.             System.out.println("demoa show run");

7.         }

8.  }

复制代码

   DemoB.java  

1.  package packb;

2.  public class DemoB{

3.  //protected修饰的用法???如果method的方法属于子类覆盖。它的父类不在同一个包中。

4.         protected void method(){

5.             System.out.println("demob show run" );

6.        }

7.  }

8.   

复制代码

   PackageDemo.java

1.  package mypack;

2.   

3.  class PackageDemo{

4.         publicstatic void main(String[] args){

5.              packa.DemoA d = new packa.DemoA();

6.              d.show();//调用A中的show

7.   

8.              packb.DemoB b = new packb.DemoB();

9.  //b中的method方法,既不在该包,又不存在子类关系。

10.             //b.method();//报错!无法访问DemoB中的protected修饰的method方法对同包中的可见

11.             System.out.println("Hello Package!");

12.        }

13. }

14.  

复制代码

    运行结果:


    包之间的访问:被访问的包中的类权限必须是public的。    
    类中的成员权限:public或者protected。
    protected是为其他包中子类提供的一种权限

    四种权限

 

    import
    一个程序文件中只有一个package,但可以有多个import

    示例:
    DemoA.java

1.  package packa;

2.   

3.  public class DemoA extends packb.DemoB{//A继承B

4.         public void show(){

5.             method();

6.             System.out.println("demoa show run");

7.         }

8.  }

复制代码

    DemoB.java  B是类。

1.  package packb;

2.  public class DemoB{

3.         protected voidmethod(){//用protected提供了对子类的访问

4.             System. out.println("demob show run" );

5.        }

6.  }

复制代码

    PackageDemo.java

1.  package mypack;

2.  //import packa.DemoA;//导入了 packa包中的DemoA类。

3.  import packa.*; //导入了packa包中所有的类。*代表所有;

4.  //导入A

5.  class PackageDemo{

6.         publicstatic void main(String[] args){

7.             DemoA d = new DemoA();//为什么先,打印B???

8.  一、method访问其它类中有protected的method

9.  二、protected能被该类的子类所访问,子类可以和父类不在一个包中。

10. //A已经导入进同一个包,可以调用

11.            d.show();

12.       }

13. }

14.  

复制代码

   运行结果:

 

 


    示例:
    有两个类:DemoA、DemoAbc。
    所在文件目录如下:
    packa\DemoA.class
    packa\abc\DemoAbc.class


    导包语句如下:
    import packa.*;
    import packa.abc.*;

    Jar包:   Java的压缩包
    方便项目的携带
    方便使用,只要在classpath设置jar路径即可。
    数据库驱动,SSH框架等都是以jar包体现的。

    Jar包的操作:
    通过jar.exe工具对jar的操作。

    创建jar包:
    jar  -cvf  mypack.jar  packa packb

    查看jar包
    jar  -tvf  mypack.jar   [>定向文件]

    解压缩
    jar  -xvf  mypack.jar

    自定义jar包的清单文件
    jar–cvfm  mypack.jar  mf.txt  packa packb

5、多线程


    5.1.1 进程、线程、多进程的概念
    进程:正在进行中的程序(直译)。
    线程(正在进行程序)中一个负责程序执行的控制单元(执行路径)。

    P.S.
    1、一个进程中可以有多个执行路径,称之为多线程
    2、一个进程中至少要有一个线程。
    3、开启多个线程是为了同时运行多部分代码,每一个线程都有自己运行内容,这个内容可以称为线程要执行的任务

    多线程的好处:解决了多部分代码同时运行的问题。
    多线程的弊端:线程太多,会导致效率降低
    其实,多个应用程序同时执行都是CPU在做着快速的切换完成的。这个切换是随机的。CPU的切换是需要花费时间的,从而导致了效率降低

 

JVM启动时启动了多条线程,至少两个线程可以分析的出来:

 

    1. 执行main数的线程,该线程的任务代码都定义在main函数中。
    2. 负责垃圾回收的线程。

    示例:

1.  class Demo extends Object{//继承对象的祖宗

2.        public void finalize(){

3.             System.out.println("demook");

4.        }

5.  }

6.   

7.  class ThreadDemo{

8.        public static void main(String[] args){

9.              new Demo();

10.             new Demo();

11.             System.gc();//垃圾回收线程

12. //呼叫java虚拟机的垃圾回收器运行回收内存垃圾

13.             new Demo();

14.             System.out.println("HelloWorld!");

15.      }

16. }

17.  

复制代码

   运行结果:

 

    像这种情况,之所以先打印Hello World!再打印demo ok,是因为两条线程是分别执行的

 


    像这种情况,只打印一个demook,是因为在垃圾回收器还没回收第二个Demo对象的时候,JVM就已经结束了。说明垃圾回收不一定马上执行。

    P.S.

 

    System类的gc方法告诉垃圾回收器调用finalize方法,但不一定立即执行。

 

    5.1.2 创建线程方式一:继承Thread类

1. 定义一个类继承Thread类。
    2. 覆盖Thread类中的run方法
    3. 直接创建Thread的子类对象创建线程
    4. 调用start方法开启线程并调用线程的任务run方法执行。

 

    单线程程序示例:

1.  class Demo{

2.       private String name ;

3.       Demo(String name){//构造函数

4.              this.name = name;

5.       }

6.        public void show(){

7.              for(int x = 0; x < 10; x++){

8.                  System.out.println(name + "...x=" + x);

9.             }

10.      }

11. }

12.  

13. class ThreadDemo{

14.       public static void main(String[] args){

15.            Demo d1 = new Demo("旺财");//name=旺财

16.            Demo d2 = new Demo("小强");

17.            d1.show();

18.            d2.show();

19.      }

20. }

21.  

复制代码

   运行结果:


    可以看到在单线程程序中,只有上一句代码执行完,下一句代码才有执行的机会。

创建线程的目的就是为了开启一条执行路径,去运行指定的代码和其他代码实现同时运行,而运行的指定代码就是这个执行路径的任务。

    jvm创建的主线程的任务都定义在主函数中

 

而自定义的线程,它的任务在哪儿呢?
    Thread类用于描述线程,线程是需要任务的。所以Thread类也有对任务的描述。

线程的任务就是通过Thread中的run方法来体现。

也就是说,run方法就是封装自定义线程运行任务的函数,run方法中定义的就是线程要运行的任务代码。

    开启线程是为了运行指定代码,所以只有继承Thread类,并复写run方法,将运行的代码定义在run方法中即可

    多线程程序示例:

1.  class Demo extends Thread{//1,继承Thread

2.        private String name ;

3.       Demo(String name){

4.              this.name = name;

5.        }

6.         publicvoid run(){//2,复写run方法

7.              for(int x = 0; x < 10; x++){

8.                   System.out.println(name +"...x=" + x + "...ThreadName=" +Thread.currentThread ().getName());

9.             }

10.       }

11. }

12.  

13. class ThreadDemo{

14.        publicstatic void main(String[] args){

15.            Demo d1 = new Demo("旺财");

16.            Demo d2 = new Demo("xiaoqiang");

17.            d1.start(); //开启线程,调用run方法。

18.            d2.start();

19.            for(int x = 0; x < 20; x++){

20.                  System.out.println("x =" + x + "...over..." +Thread.currentThread().getName());

21.            }

22.       }

23. }

24.  

复制代码

    运行结果:


    P.S.
    1、可以通过Thread的getName方法获取线程名称,名称格式:Thread-编号(从0开始)。
    2、Thread在创建的时候,该Thread就已经命名了。源码如下:


 

你可能感兴趣的:(java学习笔记)