111
/*
Java的应用领域:安卓的应用程序使用Java语言编写
什么是程序?计算机执行某些操作或解决某个问题而编写一系列有序指令的集合
Java的诞生:1995年Sun公司开发了java ;2009年Oracle收购了Sun公司 ; 其中2004年的java5.0和2014年的java8.0更新力度最大
因为有JVM(虚拟的计算机),同一个Java程序在三个不同的操作系统(Windows/Linux/Mac)都可以可以执行
java特性:面向对象opp ,跨平台的,Java语言是解释性语言,编译后的代码,不能直接被机器执行,需要解释器来执行。编译性语言(C/C++),可以直接被机器执行
Java SE标准版 Java EE企业版 Java ME小型版
JDK(java开发工具包)=JRE(运行环境)+开发工具类 JRE=JVM+Java SE标准类库
1+1在二进制中不等于2,一个小目标8个0,bit比特位 Byte字节 KB MB GB TPEZ 带tp的ez /正斜杠 \反斜杠
*/
public class HelloWorld {//表示HelloWorld是一个路,是一个public共有的类 {}表示一个类的开始和结束
public static void main(String[] args){//主方法程序的入口 {}表示一个方法的开始和结束
System.out.println("HelloWorld");//输出语句 ;表示语句的结束
}
}
class HelloWorldOne{//HelloWorldOne是一个类,编译后每一个类都会对应一个.class
public static void main(String[] args){
System.out.println("One类执行");
}
}
//通过运行工具java.c对字节码文件进行执行,本质将.class装载到JVM机运行 源文件基本组成部分是类(class)
//一个源文件最多只能有一个public类,其他类不限个数,也可以将main方法写在非public类中,然后指定运行非public类这样入口方法就是非public的main方法
//工作需求/技术控--->传统技术能解决,但不完美/不能解决----->引领我们学习新的知识点----->学习新技术或者知识点一定不要考虑细节---->快速入门----->开始研究技术注意事项,永无止境
222
/*public class Object {
//成员变量 访问修饰符(控制属性的访问范围 public proctected 默认 private) 属性有默认值整形0,浮点类型0.0,字符类型、u0000,boolean false,String null
//Java内存的结构分析 栈(基本数据类型局部变量),堆(存放对象,new出来的东西),方法区(常量池常量,字符串和类的加载信息),寄存器(和CPU相关),本地方法栈(与操作系统相关)
//类的加载信息只会加载一次 当程序执行到方法时,就会开辟一个独立的栈空间
//成员方法的好处:提高代码复用性;将细节封装起来,然后供其他用户调用即可
public static void main(String[] args) {
*//*Compute one=new Compute();//跨类方法需要通过创建对象调用
int array1[]=one.numberCompute(2,5);
System.out.println("和"+array1[0]);
System.out.println("差"+array1[1]);*//*
judgementNumber one=new judgementNumber();
if(one.is(5)){
System.out.println("偶数");
}else{
System.out.println("奇数");
}
}
}
class myMain{
public void print(int number){
System.out.println("要输出的数字是"+number);
}
public void sayOk(){
print(10);//同一类中直接调用
System.out.println("我很OK");
}
}
*//*class Compute{
//一个方法只能有一个返回值,要传递多个返回值,需要返回数组
//方法不能嵌套定义
public int[] numberCompute(int number1,int number2){
int array[]=new int[2];
array[0]=number1+number2;
array[1]=number1-number2;
return array;
}
}*//*
class judgementNumber{
public boolean is(int number){
return number%2==0;
}
}*/
//成员方法的传参机制:基本数据类型(值拷贝),引用数据类型(址拷贝)
/*public class Object {
public static void main(String[] args) {
//递归执行一个方法时,会创建一个独立的栈空间;如果使用的是引用数据类型,就会共享该引用类型的数据
*//* System.out.println(Question1(5));
System.out.println("第一天有"+peach(1)+"桃子");
//3.迷宫问题
int[][] map=new int[8][7];//迷宫用二维数组表示
for (int i = 0; i < 7; i++) {
map[0][i]=1;
map[7][i]=1;
}
for (int i = 0; i < 7; i++) {
map[i][0]=1;
map[i][6]=1;
}
map[3][1]=1;map[3][2]=1;
map[2][2]=1;//测试回溯现象
findWay(map,1,1);
System.out.println("=====路径=====");
for (int i = 0; i < map.length; i++) {
for(int j=0;j<map[i].length;j++){
System.out.print(map[i][j]+" ");
}
System.out.println();
}*//*
move(3,'a','b','c');
*//*
八皇后在8×8格的国际象棋上摆放八个皇后,使其不能互相攻击,
即:任意两个皇后不能处于同一行、同一列或同一斜线上,问有多少种摆法
这里用一维数组存放数据就可以了,这里一维数组中的值存放的是皇后的列坐标,
因为规定皇后是不能摆放在同一行,所以每一行只有一个皇后 ; 一维数组 array
的第一个值就是 棋盘第一行皇后的列坐标值,第二个值就是皇后在棋盘第二行的列坐标值
*//*
}
//1.斐波那契数列问题
public static int Question1(int number){
if(number>=1){
if(number==1||number==2){
return 1;
}else{
return Question1(number-1)+Question1(number-2);
}
}else{
System.out.println("要求number>=1的整数");
return -1;
}
}
//2.猴子吃桃问题 每天猴子吃其中一半,在多吃一个,第十天只有一个桃子,问最初有多少个桃子
public static int peach(int day){
if(day==10){
return 1;
}
else if(day>=1&&day<=9){
return (peach(day+1)+1)*2;
}else{
System.out.println("数据不合法,返回-1");
return -1;
}
}
//3.出迷宫问题
public static boolean findWay(int map[][],int row,int col){
*//*findWay找迷宫的路径,找到返回true,找不到false
row 和col表示我现在的位置
map数组各个值的含义 0表示可以走 1表示障碍物 2表示可以走 3表示可以走,但走不通
走路策略下->右->上->左
*//*
if(map[6][5]==2){
return true;
}
else{
if(map[row][col]==0){//位置是0,可以走
map[row][col]=2;//假设可以走通
if(findWay(map,row+1,col)){//下
return true;
}else if(findWay(map,row,col+1)){//右
return true;
}else if(findWay(map,row-1,col)){//上
return true;
}else if(findWay(map,row,col-1)){//左
return true;
}else{
map[row][col]=3;
return false;
}
}else{
return false;
}
}
}
//4.汉诺塔问题
public static void move(int number,char one,char two,char three){
if(number==1){
System.out.println(one+"->"+three);
}else{
//先移动所有盘子到two
move(number-1,one,three,two);//多个盘子先看成两个,最下面和上面的盘子
//再把最下面盘子放到three
System.out.println(one+"->"+three);
move(number-1,two,one,three);
}
}
}*/
//方法重载(减轻起名问题和记名的麻烦)方法名相同,参数类型个数或顺序至少一个不同,返回类型和参数名无要求
/*public class Object {
public static void main(String[] args){
int array[]={1,2,3};
//可变参数的实参可以为数组 可变参数的本质就是数组
//System.out.println(sum(array));
System.out.println(out("开炮",5,6));
}
*//*public static int sum(int... numbers){//int...表示可变参数,类型int
//一个形参列表只能出现一个可变参数
System.out.println("长度="+numbers.length);
return 0;
}*//*
public static String out(String one,int...numbers){
//可变参数可以和普通类型的参数一起放在形参列表,但必须保证可变参数要放到最后
int sumNumber=0;
for(int i=0;i<numbers.length;i++){
sumNumber+=numbers[i];
}
return "意大利炮发射"+sumNumber+"次";
}
}*/
//不给全局变量赋值也可以直接使用因为有默认值;局部变量必须赋值
//属性(成员变量)和局部变量可以重名,访问时遵循就近原则 属性伴随方法,局部伴随代码块 局部变量不可以加修饰符,属性可以
/*public class Object {
public static void main(String[] args){
*//*
前面创建人类对象时,先把对象创建好,再给他的年龄和姓名等属性赋值;
如果现在创建人类对象,就直接指定这个对象的年龄和姓名,这事就使用到了构造方法/构造器
他的主要作用是完成对新对象的初始化;在创建对象时,系统自动调用该类的构造器完成对对象的初始化,并不是创建对象
*//*
*//*Person one=new Person();
System.out.println("main->"+one.hashCode());//将对象的内部地址转化成一个整数*//*
//this访问成员方法的语法 this.方法名(参数列表)
//访问构造方法语句 this(参数列表) 注意只能在构造器中使用(只能在构造器中访问另一个构造器)
*//* Person one=new Person("阿伟",20);
Person two=new Person("奥特曼",18);
System.out.println(one.compare(two));*//*
Judge one=new Judge();
//double array[]=null;//引用类型可以赋null
double array[]={1.11,1.21,1.31};
if(one.max(array)!=null){
System.out.println("array的最大值"+one.max(array));
}else{
System.out.println("输入有误");
}
//简单的说:那个对象调用,this就代表那个对象
}
}
*//*class Person{//方法名和类名相同
*//**//* String name;
int age=18;//显示初始化
//构造器的修饰符可以默认
*//**//**//**//*public Person(String pName,int pAge){//没有返回值
System.out.println("构造器被调用~完成对象的属性初始化");
name=pName;
age=pAge;
}//javap反汇编*//**//**//**//*
public Person(){//无参构造器 构造器可以重载 不写系统也会自动给
this("龙" ,1998);//this访问构造方法时 必须放置第一条语句
System.out.println("无参");
}
public Person(String name,int age){
this.name=name;
this.age=age;
System.out.println("name age->"+hashCode());
System.out.println("有参");
}*//**//*
String name;
int age;
public Person(String name,int age){
this.name=name;
this.age=age;
}
public boolean compare(Person one){
return this.name.equals(one.name)&&this.age==one.age;
}
}*//*
class Judge{
public Double max(double[] array){
if(array!=null&&array.length>0) {//先完成正常任务,在考虑代码的健壮性
double max = array[0];//先假设第一个元素就是最大值
for (int i = 0; i < array.length; i++) {
if (max < array[i]) {
max = array[i];
}
}
return max;
}else{
return null;//返回值double不能以null返回,但Double可以
}
}
}*/
/* out--->存放编译后的 .class文件 src--->源码文件 .java
补全代码 alt + /
快速格式化代码 ctrl + alt + L
生成构造器 alt + insert[提高开发效率]
查看当前类的层级关系 ctrl + H[学习继承很有用]
自动分配变量名 .var
查看那些模板快捷键
File->Settings->Editor->Live templates模板(sout,main等)可以高效的完成开发,提高速度
包的作用:当类很多时,可以更好地管理类 package(关键字) com.test(包含) package声明当前类所在包,需要放在类最上面,一个类只能有一个package
包的本质 创建不同文件夹存放类文件
包的命名规则:数字,字母,下划线和小圆点(.),数子不能开头,不能是关键字和保留字
包的命名规范: 一般小写字母+小圆点 com.公司名.项目名.业务模块名 com.tengxun.game.hero
java.lang.* lang是基本包,默认引入
java.util.*(表示包下所有类都引入) 系统提供的工具包 java.util.Scanner表示只会引入java.util包下的Scanner
java.net.* 网络包(网络开发)
java.awt.* java的界面开发
*/
/*
访问修饰符:(访问权限)(修饰属性,成员方法和类)(只有public和默认才能修饰类)
public 对外公开 (同类 同包 子类 不同包)
protected 对子类和同一个包的类公开 (同类 同包 子类 )
默认 同一个包的类公开 (同类 同包 )
private 只能类本身可以访问,不对外公开 (同类 )
*/
//面向对象的三大特征:封装(隐藏实现细节) 继承 多态
/*class Person{
//将属性进行私有化
public String name;
private int age;
private double salary;
public Person() {
}
public Person(String name, int age, double salary) {
setName(name);//把set写在构造器中,
setAge(age);
setSalary(salary);
}
public String getName() {
return name;
}
public void setName(String name) {//提供一个公共的set方法,用于对属性判断并赋值
if(name.length()>=2&&name.length()<=6){
this.name = name;
}else{
System.out.println("名字长度超出范围,无法显示,抱歉,将默认为无名");
this.name="无名";
}
}
public int getAge() {//提供一个公共的get方法,用于获取属性的值
return age;
}
public void setAge(int age) {
if(age>=0&&age<=100){
this.age = age;
}else{
System.out.println("年龄超出正常范围,无法显示,抱歉,将默认为18");
this.age=18;
}
}
public double getSalary() {
return salary;
}
public void setSalary(double salary) {
this.salary = salary;
}
}
public class Object {
public static void main(String[] args) {
Person one=new Person("阿伟",2000,900);
System.out.println("姓名"+one.getName()+"年龄"+one.getAge()+"工资"+ one.getSalary());
}
}*/
/*继承(提高了代码的复用性和维护性) class 子类 extends 父类{} 父类又叫超类,基类 子类又叫派生类
细节1:父类中的私有属性不能在子类直接访问,要通过公共方法去访问 ,属性(public int getName(){}等)/成员方法(公共调用private的方法)
2.创建子类对象,先调用父类的构造器完成初始化,若父类没有提供无参构造器,则必须在子类中指定使用父类那个构造器完成对父类初始化操作;否则编译不通过
调用父类无参构造器,要么什么都不写,要么写super(); //super()和this()必须放在第一行,因此这两个方法不能共存在一个构造器中
3.java所有类都是Object的子类 父类构造器的调用一直到Object(只是这个顶级父类什么都不打印罢了);如果要查找的信息子类没有,则向上查找,如果到Object还没有,则报错
4.java子类父类继承是单继承(子类只能有一个父类)
5.不能滥用继承,必须要满足逻辑关系 Music extends Person 音乐继承人??? Cat extends Animal 猫继承动物 yes yes yes
*/
/*
方法的重写:子类的参数,方法名称和父类的参数方法名称一样;子类的返回类型和父类的返回类型一样,或者是父类返回类型的子类;子类的方法不能缩小父类方法的访问权限
重写和重载的区别:1.发生范围(父子类,本类) 2.方法名(必须一样) 3.形参列表(相同,类型个数顺序至少有一个不同) 4.返回类型(子类返回类型是父类的子类或相同,无要求) 5.修饰符(子类的访问方法大于等于父类,无要求)
*/
/*多态(提高代码的复用性和维护性) 多态是建立在封装和继承基础之上的
多态的具体体现:1.方法的多态(重写和重载--根据对相不一样,调用的方法也不一样)
2.对象的多态(Person one = new xiaoMing();举例) //假如xiaoMing是Person的子类对象
=左边是编译类型(Person);等号右边是运行类型(xiaoMing);
一个对象的编译类型和运行类型可以不一样,运行类型是可以变化的(也可以new Person();)
编译类型在定义对象时,就确定了,不能改变(就相当于人一生下来就有亲生父亲,你可以认干爹,但不能改变亲生父亲)
多态的前提是:两个对象存在继承关系 本质:父类的引用指向子类对象(向上转型) 可以调用父类的所有成员(特殊成员除外)(能调用那些类型是由编译类型决定的),最终运行效果看右边的运行类型
如果要调用父类的特殊成员需要向下转型 xiaoMing one = new (xiaoMing)Person;(编译是xiaoMing,运行用了强转也是xiaoMing) 只能强转父类的引用,不能强转父类的对象;要求父类的引用必须指向当前目标类型的对象,才可以调用子类的所有成员
属性没有重写之说,属性的值看编译类型
instanceOf比较操作符,用于判断对象类型是否为某个类的类型或某个类的子类型
java的动态绑定机制:1.当调用对象方法时,该方法会和该对象的内存地址/运行类型绑定 2.当调用对象属性时,没有动态绑定机制,那里声明,那里使用
//多态数组:数组的定义类型为父类类型,里面保存的实际元素类型为子类类型 Person[] person = new Person[3]; 遍历的时候person.length
==基本类型判断值,引用类型判断地址 equals只能判断基本类型(默认判断地址是否相等,子类往往重写该方法,用于判断内容是否相等)
equals(Object类的方法,Java类都可以使用equals)
*/
333
//Java常见的转义字符
/*public class One {
public static void main(String[] args) {
System.out.println("你好\t北京");
System.out.println("你好\n上海");// \n换行
System.out.println("D:\\新建文件夹 (11)\\Start"); // \\两个转义一个\
System.out.println("我说:\"你要好好学Java\""); // 转义一个"
System.out.println("我说:\'你要好好学Java\'");// 转义一个'
System.out.println("你好你好\r成都");//回车和换行不一样
//选中Tab整体右移 Shift+Tab整体左移
}
}*/
//多行注释不允许嵌套
/**
* @author 阿伟
* @version 5.0
*/
//文档注释可以被Javadoc所解析,生成一套以网页文件形式体现的该程序的文档 javadoc -d 文件夹名 -xx -yy One.java
/*
DOS(磁盘操作系统) 相对路径:从当前目录开始定位,形成一个路径 绝对路径:从顶级目录开始定位
dir查看当前目录内容 cd进入其他目录 cd ..返回上一级 cd\切换根目录 tree查看指定目录所有子集目录 清屏cls 退出exit md创建文件 rd删除文件 move剪切文件 echo输入内容到文件 copy拷贝文件 del删除文件
坏境变量的作用是为了在dos的任意目录,可以使用java和javac命令
*/
//变(变化)量(值)
/*
public class One{
//加法(+)当左右两别都是数值型,做加法运算;当左右两边一方为字符串,则做拼接运算
public static void main(String[] args){
System.out.println(100+3);
System.out.println("Hello"+100+3);//打印结果Hello1003
}
}*/
/*
Java数据类型
数据类型:基本数据类型(整数类型byte,short,int21个亿,long,浮点类型double,float,字符类型char(2字节),布尔类型(1字节)boolean)
引用数据类型(类,数组,接口)
java中默认整数类型是int(使用long类型要加L),浮点类型是double(使用float要加F)
浮点数可能只是一个近似值并非精确值(1/3)double 和 float区别
数据的范围与字节数无关,float(四个字节)比long(八个字节)数据范围更广泛
*/
/*public class One{
public static void main(String[] args){
System.out.println(.512);//正确 必须加小数点
System.out.println(5.12E-1);//科学计数法表示
System.out.println(5.12E1);//科学计数法表示
//单精度和双精度的区别
System.out.println(3.141592654F);
System.out.println(3.141592654);
//浮点数的使用陷阱
double number1=2.7;
double number2=8.1/3;
System.out.println(number1);
System.out.println(number2);//打印的是一个接近2.7的数 计算机不知道8.1后面还有没有数字
//所以对小数进行判断时,用两个数差值的绝对值,在某个精度范围判断
if(Math.abs(number1-number2)<0.000001){
System.out.println("差度非常小,到我的规定精度,认为相等");
}
//在java中,char本质是一个整数,在默认输出时,是unicode码对应的字符
char number3=97;
System.out.println(number3);
System.out.println(number3+1);//char类型可以进行运算
char number4='a';
//要输出对应的数字,可以(int)字符
System.out.println((int)number4);
//java允许使用转义字符
char number5='\n';
*//*
字符串存储 'a'--->码值97--->二进制---->存储
读取 二进制--->码值--->'a'--->显示
ASCII一个字节表示,可以表示256个字符,但只用了128个 缺点:不能表示所有字符
Unicode字母和数字同一都是两个字节 Unicode是兼容ASCII码 缺点浪费空间
utf-8 大小可变的编码(根据不同的符号来变化字节长度),互联网使用最广的一种,对Unicode的改进 字母使用一个字节 汉字用三个字节
gbk字母一个字节,汉字两个字节 gbk>gb2312
big5码 (繁体中文,香港台湾)
*//*
//boolean类型,不能用0或非0值替代false和true,这点和C语言不同
//基本类型数据转化 精度小到大(自动类型转换) 大到小(强转)
byte number6=10;//把具体值赋给number6时,先判断是否在byte范围内
int number7=number6;//如果是变量赋值,则先判断类型
//byte(short)和char之间不会相互转换,他们三者计算时,先转换为int类型 boolean不参与转换
byte number8=1;
// byte number9=number6+number8;//会报错 左边int右边byte
int number9=number6+number8;//正确
System.out.println(number9);
//强转只针对于最近的操作数有效 (int)5*8 把5强转为int再相乘
//基本数据类型转String
String number10=number6+"";//基本类型值+""
System.out.println(number10);
//String转基本数据类型(首先格式要正确,确保数据的有效性,"hello"就不能转化成基本数据)
String number11="123";
byte number16=Byte.parseByte(number11);
short number17=Short.parseShort(number11);
int number12=Integer.parseInt(number11);
double number13=Double.parseDouble(number11);
float number14=Float.parseFloat(number11);
long number15=Long.parseLong(number11);
boolean number18=Boolean.parseBoolean("true");
System.out.println(number12);
System.out.println(number13);
System.out.println(number14);
System.out.println(number15);
System.out.println(number16);
System.out.println(number17);
System.out.println(number18);
double number19=10/4;//右边是int相除
double number20=10.0/4;
System.out.println(number19);//打印结果2.0
System.out.println(number20);//打印结果2.5
//取模的本质 a%b=a-(a是小数则加int)a/b*b
System.out.println(10%-3);//套公式 10-10/(-3)*(-3) 1
System.out.println(-10%3);// -10-(-10)/3*3 -1
System.out.println(-10%-3);// -10-(-10)/(-3)*(-3) -1
// 先认识一下:instanceof(检查是否是类的对象)
//逻辑运算符 && ||(短路效果,效率高) & |(逻辑与,逻辑或) ^逻辑异或(当a和b不同时,则结果为true)
boolean number21=(10>5)^(5<10);
boolean number22=(10<5)^(5<10);
System.out.println(number21);
System.out.println(number22);
//复合赋值运算符会进行类型转换
byte number23=5;
number23 +=2;//numebr23=(byte)(number23+2)
System.out.println(number23);
number23++;//number23=(byte)(number23+2)
System.out.println(number23);
//运算符具有优先级 只有单目运算符,赋值运算符是从右向左运算的
*//*标识符的规则(必须执行)
标识符由26个英文字母,0-9和 _ 或 $ 组成 ; 不可以数字开头;不可以使用关键字和保留字
保留字:现在版本尚未使用,但以后可能会作为关键字使用
规范:包(小写) com.lsp.day 包包括:接口,类和异常
类名/接口 大驼峰
变量名/方法名 小驼峰
常量名 全部大写
//进制 二进制 0b/oB 开头
八进制 0开头
十六进制 0x/0X开头
// 0的反码补码都是0 计算机以补码方式来运算,看运算结果要看原码
*//*
System.out.println(~-2);//打印1
// -2原码 10000000 00000000 00000000 00000010 反码 11111111 11111111 11111111 11111101 补码11111111 11111111 11111111 11111110
//按位取反(符号位也变) 00000000 00000000 00000000 00000001
//算数右移(/2) >> 算数左移(*2)<< 无符号右移(逻辑右移)>>>
}
}*/
/*public class One{
public static void main(String[] args){
//导包 import java.util.Scanner
Scanner scanner=new Scanner(System.in);
System.out.println("请输入姓名");
String name=scanner.next();
System.out.println("请输入性别");
char gender= scanner.next().charAt(0);
System.out.println("请输入年龄");
int age=scanner.nextInt();
System.out.println("请输入价格");
double price=scanner.nextDouble();
System.out.println("姓名:"+name+"性别"+gender+"年龄:"+age+"价格:"+price);
double number1=23d;//不会报错 跟25f类似
//switch(表达式对应一个值,可以是byte,short,int,char,enum,String)
//case常量 表达式的数据类型应和case后的一致,或者可以自动转换char(int)
}
}*/
//API Java字典
/*public class One{
public static void main(String[] args){
//for只有一条语句,可以省略{},建议不要省略
//初始化和调整部分可以写在其他地方
*//*int frequency=1;
for(;frequency<5;){
System.out.println("HelloWorld");
frequency++;
}
System.out.println("====================");
//初始化可以有多条语句,但要类型一致;调整部分也可以多条语句
for(int frequency1=2,frequency2=10;frequency1<frequency2;frequency1++,frequency2--){
System.out.println("你好,世界");
}*//*
//for while do...while嵌套循环时,最多不要超过三层,否则代码可读性很差 外层循环n次,内层循环m次,总共循环m*n
//打印矩形
*//* int total=5;//先死后活
for (int i = 0; i < total; i++) {//层数
for (int i1 = 1; i1 < 3; i1++) {
System.out.print("*****");
}
System.out.println();
}
//打印金字塔
for (int i = 1; i <= total; i++) {//层数
for(int k=1;k<=total-i;k++){
System.out.print(" ");
}
for(int m=1;m<=2*i-1;m++){
System.out.print("*");
}
System.out.println();
}
//打印空心金字塔
for (int i = 1; i <= total; i++) {//层数
for(int k=1;k<=total-i;k++){
System.out.print(" ");
}
for(int m=1;m<=2*i-1;m++){
if(m==1||m==2*i-1||i==total){
System.out.print("*");
}else{
System.out.print(" ");
}
}
System.out.println();
}*//*
*//* label1:
for (int i = 0; i < 5; i++) {
System.out.println(Math.random());//返回一个double值,大于0.0小于1.0
}
label2:
for (int i = 0; i < 5; i++) {
System.out.println("HelloWorld");
if(i==2){
break label2;//break 和continue都可以通过标签指明要终止那一块语句块
}
}
//字符串比较 equals
String name="从善";
System.out.println("阿伟".equals(name));//推荐,可以避免空指针
System.out.println(name.equals("从善"));
*//*
//简单实现登陆界面
*//*Scanner three=new Scanner(System.in);
String name="";
String password="";
while(true) {
System.out.println("请输入用户名");
name=three.next();
System.out.println("请输入密码");
password=three.next();
if("阿伟".equals(name)&&"666".equals(password)){
System.out.println("恭喜你,登陆成功");
break;
}
}*//*
//return写在方法,跳出方法;写在main方法,结束程序
//判断一个数是否是水仙花数
*//* Scanner one=new Scanner(System.in);
System.out.println("请输入数字");
int number=one.nextInt();
int number1=number/100;
int number2=number%100/10;
int number3=number%10;
if(number1*number1*number1+number2*number2*number2+number3*number3*number3==number){
System.out.println(number+"是水仙花数字");
}else{
System.out.println("不是");
}*//*
*//*for(char word='a';word<='z';word++){
System.out.print(word);
}
System.out.println();
for(char word='A';word<='Z';word++){
System.out.print(word);
}*//*
//求1+(1+2)+(1+2+3)+(1+2+3+4)+(1+2+...+100)
*//*int sum=0;
for(int i=1;i<=100;i++){
for(int n=1;n<=i;n++){
sum+=n;
}
}
System.out.println("sum="+sum);*//*
//数组的反转
*//* int[] array={11,22,33,44,55,66};
//int array[]={11,22,33,44,55,66};//也可以这样写
int temp=0;
for(int i=0;i<array.length/2;i++){//数组反转3次就可以亮了
temp=array[array.length-1-i];
array[array.length-1-i]=array[i];
array[i]=temp;
}
for(int i=0;i<array.length;i++){
System.out.print(array[i]+" ");
}
System.out.println();*//*
//数组扩容
Scanner one=new Scanner(System.in);
int[] array={1, 2,3};
do{
int[] arrayNew=new int[array.length+1];
for (int i = 0; i < array.length; i++) {
arrayNew[i]=array[i];
}
System.out.println("请输入你要添加的元素");
arrayNew[arrayNew.length-1]=one.nextInt();
array=arrayNew;//将array扩容
for (int i = 0; i < array.length; i++) {
System.out.print(array[i]+"\t");
}
System.out.println("是否需要继续添加Y/N");
char key=one.next().charAt(0);
if(key=='N'){
break;
}
}while(true);
}
}*/
//排序:内部排序;外部排序(大数据数据量过大)
/*public class One {
public static void main(String[] args) {
//冒泡排序:每一轮排序只能确定一个数
*//*int[] array={24,63,48,56,99};
for(int i=0;i<array.length-1;i++) {
for (int j = 0; j < array.length-1-i; j++) {
if (array[j] > array[j + 1]) {
int temp = array[j];
array[j] = array[j + 1];
array[j + 1] = temp;
}
}
}
for (int i = 0; i < array.length; i++) {
System.out.print(array[i]+"\t");
}*//*
//查找古力娜扎
*//*String[] name={"古力娜扎","马尔扎哈","迪丽热妈","迪丽热巴"};
System.out.println("请输入要查找的名字");
Scanner input=new Scanner(System.in);
int index=-1;
for(int i=0;i<name.length;i++){
if((input.next()).equals(name[i])){
System.out.println("恭喜你找到了"+"下标是"+i);
index=i;
break;
}
}
if(-1==index){
System.out.println("抱歉,没有找到");
}*//*
//二维数组每个元素是一维数组
*//* int[][] array1={{0,1,2},{3,4,5},{6,7,8}};
int[][] array2=new int[3][];
int[] array3[];//也可以这样写
//动态数组---列数不确定用 //打印1 22 333 4444 ……
for(int i=0;i<array2.length;i++){//遍历array2每一个数组
array2[i]=new int[i+1];//给每个数组开辟空间
for(int j=0;j<array2[i].length;j++){
array2[i][j]=i+1;
}
}*//*
//打印杨辉三角 第n行n个元素
*//* int[][] array3 = new int[10][];
for (int i = 0; i < array3.length; i++) {
array3[i] = new int[i + 1];
for (int j = 0; j < array3[i].length; j++) {
if (j == 0 || j == array3[i].length - 1) {
array3[i][j] = 1;
} else {
array3[i][j] = array3[i - 1][j] + array3[i - 1][j - 1];
}
}
}
for (int i = 0; i < array3.length; i++) {
for (int j = 0; j < array3[i].length; j++) {
System.out.print(array3[i][j] + "\t");
}
System.out.println();
}
*//*
//已有升序数组,插入一个元素,仍是升序数组
int[] array4={10,20,30,40,50};
int insertNum=23;
int index=-1;
for(int i=0;i<array4.length;i++){
if(insertNum<=array4[i]){
index=i;
break;
}
}
if(-1==index){
index=array4.length;
}
int[] array4New=new int[array4.length+1];
for(int i=0,j=0;i<array4New.length;i++){
if(i!=index){
array4New[i]=array4[j];
j++;
}else{
array4New[i]=insertNum;
}
}
array4=array4New;
for(int i=0;i<array4.length;i++){
System.out.print(array4[i]+"\t");
}
}
}*/
444
/*public class Demo1 {
public static void main(String[] args) {
Person person1 = new Person("奥特曼", 18);
Person person2 = new Person("奥特曼",18);
System.out.println(person1.equals(person2));//如果不重写,则输出结果为false
String one=new String("abc");
String two=new String("abc");
System.out.println(one.equals(two));//String有方法的重写
*//*
hashCode 两个引用,如果指向的是同一个对象,则哈希值肯定是一样的;哈希值是根据地址号来的,不能完全将哈希值等价于地址(java用的是虚拟机)
toString方法 默认返回:全类名(包名+类名) + @ + 哈希值的16进制 子类往往重写toString方法
*//*
System.out.println(person1.toString()+"\t"+person1.hashCode());
System.out.println(person1+"\t"+person1.hashCode());// person1等价于person1.toString()
//当某个对象没有任何引用时,则jvm就认为这是一个垃圾,就会使用垃圾回收机制销毁对象,在销毁对象前,会先调用finalize方法
//垃圾回收调用是由系统来决定,也可以通过System.gc()主动触发垃圾回收装置
Person person3=new Person("汤姆");
person3=null;
//这是person3相当于一个垃圾 (子类也可以重写finalize方法,做一些释放资源的操作(数据链接+打开文件等等))
//如果不重写,则就会调用Object类的finalize,即默认处理
System.gc();//主动调用垃圾回收器
System.out.println("程序结束");
}
}
class Person{
private String name;
private int age;
public Person(String name, int age) {
this.name = name;
this.age = age;
}
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
public int getAge() {
return age;
}
public void setAge(int age) {
this.age = age;
}
public boolean equals(Object obj){
if(this==obj){
return true;
}
if(obj instanceof Person){
Person one=(Person)obj;
return this.name.equals(one.name)&&this.age==one.age;
}
return false;
}
}*/
/*再断点调试过程中,是运行状态,是一对象的运行类型来执行
F7(跳入方法内) F8(逐行执行代码) Shift + F8(跳出方法) F9(执行到下一个断点)
*/
/*import java.text.SimpleDateFormat;
import java.util.Date;
import java.util.Scanner;
//模拟微信零钱通
public class Demo1 {
public static void main(String[] args) {
boolean label=true;
Scanner scanner=new Scanner(System.in);
String choose="";
//把收益和消费可以保存到数组,也可以使用对象,简单的话可以String拼接
String begin="--------零钱通明细--------";
//1.完成收益转账
double money=0;
double consume=0;
Date date = null;//date 是 Java.util.Date类型 表示日期
//date = new Date();System.out.println(date); 这样打印格式很怪,不符常理
SimpleDateFormat myDate=new SimpleDateFormat("yyyy-MM-dd HH:mm");//("yyyy-MM-dd HH:mm")将日期格式化
//2.消费 定义新的变量,保存消费原因
String name="";
do{
System.out.println("=========零钱通菜单=========");
System.out.println("\t\t\t1 零钱通明细");
System.out.println("\t\t\t2 收益转账");
System.out.println("\t\t\t3 消费");
System.out.println("\t\t\t4 退 出");
System.out.println("请选择1-4");
choose=scanner.next();
switch(choose){
case "1":
System.out.println(begin);
break;
case "2":
System.out.print("2 收益转账金额");
money=scanner.nextDouble();
//检验 这个if过不去直接不执行下面代码
if(money<=0){
System.out.println("收益转账应大于等于0");
break;
}
consume+=money;//记录总金额
date =new Date();//获取当前日期
begin+="\n收益转账\t+"+money+"\t"+myDate.format(date)+"\t"+consume;//拼接信息
System.out.println("收益转账成功");
break;
case "3":
System.out.println("3 消费金额");
money=scanner.nextDouble();
if(money<=0||money>consume){
System.out.println("您消费的金额应在0-"+consume);
break;
}
System.out.println("消费说明:");
name=scanner.next();
consume-=money;
date =new Date();
begin+="\n"+name+"\t-"+money+"\t"+myDate.format(date)+"\t"+consume;
System.out.println("消费成功");
break;
case "4":
String choice="";
//代码风格:一段代码实现一个功能 更加清晰明白
while(true){//用户输入Y/N否则一直循环
System.out.println("你确认要退出嘛? Y/N");
choice=scanner.next();
if("Y".equals(choice)||"N".equals(choice)){
break;
}
}
if(choice.equals("Y")){//对用户输入进行判断是否退出
label=false;
}
break;
default:
System.out.println("输入错误,请重新选择");
}
}while(label);
System.out.println("退出零钱通项目");
}
}*/
//对象运行类型是可以变化的,可以通过getClass()来查看运行类型
/*public class Demo1 {
public static void main(String[] args) {
AAA.say();//因为一个方法是static(这就是静态方法)可以直接使用
*//*AAA one=new BBB();
AAA two=one;
System.out.println("one的运行类型是"+one.getClass());
one=new CCC();
System.out.println("one的运行类型是"+one.getClass());
one=two;
System.out.println("one的运行类型是"+one.getClass());*//*
}
}
class AAA{
static void say(){
System.out.println("静态方法可以直接通过类名称调用");
}
}
class BBB extends AAA{
}
class CCC extends BBB{
}*/
//在实际开发中,公司会提供相应的工具类和开发类,可以提高效率
/*
class Child{
private String name;// 普通属性/普通成员变量/非静态属性/非静态成员变量;实例对象是每个对象独享的
//public static int count;//类变量必须遵守相关访问权限
static public int count;//也可以这样写,但不推荐
*/
/* count为类变量(静态变量) 该变量最大特点是会被Child实例化对象共享
在java7,java8等版本这个count放在方法区的静态域里面
但现在static 变量保存在Class实例的尾部 Class对象确实在堆中,static对象在类的加载的时候就生成了
*//*
public Child(String name) {
this.name = name;
}
public void join(){
System.out.println(name+"加入了战斗");
}
}
public class Demo1 {
public static void main(String[] args) {
//通过类名.类变量名访问(推荐)
Child.count++;//类变量是随着类的加载而创建,所以即使没有实例化对象也可以访问
Child child1=new Child("狐狸精");
child1.join();
child1.count++;//通过对象名.类变量名
Child child2=new Child("白骨精");
child2.join();
Child.count++;
System.out.println("共有"+child1.count+"个角色");
System.out.println("共有"+child2.count+"个角色");
}
}
*/
/*class Student{
private String name;
private static double cost;
public Student(String name) {
this.name = name;
}
//静态方法不允许使用和对象有关的关键字(this和super)
//类方法和普通方法都是随着类的加载而加载,将结构信息存储在方法区
//类方法(静态方法)只能访问静态变量和静态方法
public static void sum(double cost){//当方法使用static修饰后,该方法就是静态方法
Student.cost+=cost;
}
*//*static public void sun(double cost){// 也可以这样写,但不推荐
Student.cost+=cost;
}*//*
public static void show(){
System.out.println("总费用有:"+Student.cost);
}
}
public class Demo1 {
public static void main(String[] args) {
*//*
1.java虚拟机需要调用类的main()方法,所以该方法的访问权限必须是public
2.java虚拟机在执行类的main()方法不必创建对象,所以方法必须是static
3.该方法接受String类型的数组参数,该数组中保存执行java命令时传递给所运行类的参数
*//*
for (int i = 0; i < args.length; i++) {
//动态传值 Program arguments
System.out.println("第"+(i+1)+"参数"+args[i]);
}
//Student.sum(200);//对象名.类方法名 也可以对类方法的调用
//Student.sum(25.2);
//Student.show();
//如果我们不希望创建实例,就可以调用某个方法(当成工具来用);这时,把方法做成静态方法就非常使用
//要想访问对象中的非静态成员,必须创建一个实例化对象
}
}*/
/*
class AA{
*/
/*代码化块(初始化块)(不同通过调用或类显式调用,而是加载类或创建对象时隐式调用)
相当于另一种形式的构造器(对构造器的补充机制),如果多个构造器中都有重复的语句,可以提到初始化块中,提高代码的重复性
当我们不管调用那个构造器,创建对象,都会先调用代码块的内容
*//*
{//普通代码块
//普通代码块被创建一次就会调用一次
};// ; 可以写,也可以不写
static{//静态代码块
//静态代码块随着类的加载而执行,并且只会执行一次(1. new对象时 2. 创建对象实例,父类也会被加载,父类先加载子类后加载 3. 使用类的静态成员和静态方法,但普通代码块不会执行)
}
private static int number=getNUM();//静态属性初始化
public static int getNUM(){
return 100;
}
*/
/*
调用顺序:1.父类静态代码块或静态属性初始化(都有按他们定义顺序调用)
2.子类静态代码块或静态属性初始化(都有按他们定义顺序调用)
3.父类调用普通代码块或普通属性初始化(都有按他们定义顺序调用)
4.父类的构造方法
5.子类调用普通代码块或普通属性初始化(都有按他们定义顺序调用)
6.子类的构造方法
静态代码块只能直接调用调用静态成员(静态属性和静态方法),普通代码块可以调用任意成员
*//*
}
*/
/*
设计模式(在大量的实践中优选的代码结构,编程风格,以及思考问题的方式)
单例设计模式(对某个类只能存在一个对象(通常时重量级对象)实例,并且该类只提供一个取得其对象实例的方法)(两种方式1.饿汉式2.懒汉式)
两者区别:1.饿汉式在类的加载就创建了对象实例,而懒汉式在使用时才创建
2.饿汉式(如果一个对象是咧都没有使用,就会浪费资源),懒汉式(存在线程问题)
*/
/*class Girl{//饿汉式
private String name;
private Girl(String name) {//1.将构造器私有化
this.name = name;
}
private static Girl girl=new Girl("小红红");//2.在类中直接创建
@Override
public String toString() {
return "Girl{" +
"name='" + name + '\'' +
'}';
}
public static Girl get(){//3.提供一个公共的static方法,返回girl对象
return girl;
}
}
public class Demo1 {
public static void main(String[] args) {
Girl one=Girl.get();
System.out.println(one);
Girl two=Girl.get();
System.out.println(two);
System.out.println(one==two);
}
}*/
/*class Girl{
private String name;
private static Girl girl;//定义一个static静态属性对象
private Girl(String name) {//1.将构造器私有化
this.name = name;
}
@Override
public String toString() {
return "Girl{" +
"name='" + name + '\'' +
'}';
}
public static Girl get(){
if(girl==null){//如果没有创建对象
girl=new Girl("小可爱");
//只有当用户使用get时,才返回girl对象,下次再使用,会返回上次创建的girl对象
}
return girl;
}
}
public class Demo1 {
public static void main(String[] args) {
Girl one=Girl.get();
System.out.println(one);
Girl two=Girl.get();
System.out.println(two);
System.out.println(one==two);
}
}*/
/*
final中文意思:最后的,最终的 可以修饰类,属性,方法和局部变量
final类不能继承,但可以实例化对象
如果类不是final类,但是含有final方法,则该方法不能重写,但是可以继承
一般来说,如果一个类是final类,就没有必要再将方法修饰成final方法
final不能修饰构造方法(即构造器)
final和static搭配使用,效率更高,不会导致类加载
包装类(Integer,Double,Float,Boolean等都是final) String 也是final
*/
/*final class Person{// Person不能被其他类继承
//final修饰的属性又叫常量,常量名一般大写;必须赋初值
//public final double NUM_ONE=0.00;//不希望某个属性的值被修改
public final double NUM_ONE;
//public static final double NUM_TWO=0.02;//如果final修饰的属性是静态的;直接赋值
public static final double NUM_TWO;
static{
NUM_TWO=0.02;//在静态代码块中赋值
System.out.println("嘎嘎嘎,静态代码块执行");
}
*//*public Person() {
NUM_ONE=0.01;//在构造器中赋值
}*//*
{
NUM_ONE=0.01;//在代码块中赋值
}
public final void hello(){// hello不能被子类重写
final double NUM=0.01; //不希望局部变量被修改
}
}*/
//当父类的某些方法需要声明,但又不确定如何实现,可以将其为抽象方法,这个类就是抽象类
// abstract只能修饰类和方法,不能修饰其他的(抽象类本质是类)
//抽象方法不能使用private,final和static来修饰,因为这些关键字和重写违背
/*abstract class Animal{//抽象类不一定含有abstract方法;一但包含了abstract方法,则类必须声明为abstract
public abstract void eat();//(抽象方法没有实现的方法,没有实现是指没有方法体)
}
abstract class Cat extends Animal{
//如果一个类继承了抽象类,则它必须实现抽象类的所有抽象方法,除非他自己也声明为abstract类
}
class Dog extends Animal{
public void eat(){
}
}*/
/*public class Demo1 {
public static void main(String[] args) {
long start = System.currentTimeMillis();//得到开始时间
long num = 0;
for (long i = 1; i < 80000; i++) {
num += i;
}
long end = System.currentTimeMillis();//得到结束时间
System.out.println("执行时间" + (end - start));
}
}*/
//接口的修饰符只能是public 和默认(这点和类很像)
/*public interface Demo1 {//接口不能被实例化
int number=10;//等价于 public static final int number = 10;
public void job();//在接口中,抽象方法可以省率abstract关键字
//在Jdk7前,接口所有方法都没有方法体,即都是抽象方法
public static void input(){//在Jdk8后,可以有静态方法
System.out.println("开始输入");
}
void out();
default public void stop(){//在Jdk8后,可以有默认实现方法,需要default关键字修饰
System.out.println("停止工作");
}
}
class Worker implements Demo1{// implements实现接口(需要将该接口所有抽象方法都实现)
@Override
public void job() {
System.out.println("Usb接口开始工作");
}
@Override//Alt + Enter
public void out() {//接口所有方法是public方法
}
}
interface Usb1{
}
interface Usb2{
}
class Usb implements Usb1,Usb2{//一个类可以实现多个接口
}
interface MyUsb extends Usb1,Usb2{//接口不能继承其他类,但可以继承多个接口
}*/
/*interface Test{
int number=100;
}
class MyTest implements Test{
}
public class Demo1 {
public static void main(String[] args) {
MyTest test=new MyTest();
System.out.println(test.number);
System.out.println(Test.number);//接口名.属性名
System.out.println(MyTest.number);// number是static修饰过的
}
}*/
/*
class Monkey{
private String name;
public Monkey(String name) {
this.name = name;
}
public void ability(){
System.out.println("猴子捞月");
}
}
interface Fish{
void swimming();
}
class WuKong extends Monkey implements Fish{
//当子类继承父类,就拥有了父类的功能;当子类需要扩展功能,可以通过实现接口的方法扩展(可以理解为接口是对java单继承的补充)
public WuKong(String name) {
super(name);
}
@Override
public void swimming() {
System.out.println("化鱼下五洋捉鳖");
}
}
public class Demo1 {
public static void main(String[] args) {
WuKong one=new WuKong("六耳猕猴");
one.swimming();
one.ability();
}
}
*/
/*
接口(设计好各种规范,让其他类实现)和继承(解决代码复用性和维护性)
接口(like-a)比继承(is-a)更加灵活
*/
/*interface Usb{
void job();
}
class One implements Usb{
@Override
public void job() {
System.out.println("One开始工作了");
}
public void stop(){
System.out.println("太累了,发烫");
}
}
class Two implements Usb{
@Override
public void job() {
System.out.println("Two开始工作了");
}
}
public class Demo1{
public static void main(String[] args) {
//接口多态的体现
//接口类型的变量 one可以指向实现Usb接口的对象实例
*//*Usb one=new One();//和继承 AAA one= new BBB(); one=new CCC(); AAA是BBB和CCC的父类
one=new Two();*//*
//多态数组
Usb[] usbs=new Usb[2];
usbs[0]=new One();
usbs[1]=new Two();
for(int i=0;i<usbs.length;i++){//遍历usbs数组
usbs[i].job();//动态绑定
if(usbs[i] instanceof One){//进行向下转型 调用One的特有方法
((One)usbs[i]).stop();
}
}
}
}*/
/*
一个类又嵌套了另一个类,被嵌套的类成为内部类 嵌套其他类的类称为外部类 内部类最大的特点就是可以直接访问私有属性
*/
/*
class One{//类的五大成员:1.属性 2.方法 3.构造器 4.代码块 5.内部类
private int number=100;//属性
public One(int number) {//构造器
this.number = number;
}
public void hi0(){//方法
}
public void hi(){
System.out.println("方法执行了");
//不能添加访问修饰符,但可以用final修饰
final class One2{//局部内部类(本质是一个类)(地位是一个局部变量,外部其他类不能访问)
//如果外部类和局部类的成员重名,默认遵循就近原则,访问外部类的成员,则可以使用(外部类名.this.成员)
private int number=200;
public void hi1(){
//可以直接访问外部类的所有成员,包含私有的
//One.this本质就是外部类对象,即那个对象调用了number,One.this就是那个对象
System.out.println("内部类的number="+number+"外部类的number="+One.this.number);
}
}
//创建One2对象,就可以调用即可
One2 one2=new One2();
one2.hi1();
}
{//代码块
System.out.println("代码块执行了");
}
class One1{//内部类
}
}
public class Demo1 {
public static void main(String[] args) {
One a=new One(100);
a.hi();
}
}
*/
/*interface Usb{
public void voice();
}
abstract class Usb1{
abstract void test();
}
public class Demo1 {
public static void main(String[] args) {
*//*
如果一个类只使用一次,后面不再使用,就可以用匿名对象来简化开发
匿名对象类(1.本质是类 2.内部类 3.该类没有名字 4.同时还是一个对象)
phone的编译类型 Usb
phone的运行类型 匿名对象类(匿名对象类只能使用一次) XXX => Demo1$1
(jdk底层在创建匿名对象Demo1$1,立马创建了Demo1$1实例,并把地址返回给phone)
底层: class XXX implements Usb{
@Override
public void voice() {
System.out.println("手机播放音乐");
}
}
*//*
*//* Usb phone=new Usb(){
@Override
public void voice() {
System.out.println("手机播放音乐");
}
};
phone.voice();
System.out.println("phone的运行类型="+phone.getClass());
//基于抽象类的匿名对象类
*//**//*Usb1 usb1=new Usb1() {
@Override
void test() {
System.out.println("test执行了");
}
};
usb1.test();*//**//*
//也可以直接调用
new Usb1() {
@Override
void test() {
System.out.println("test执行了");
}
}.test();*//*
test1(new Usb(){//匿名对象当作实参之间传递(最佳实践)
@Override
public void voice() {
System.out.println("我要说话了");
}
});
}
public static void test1(Usb usb1){
usb1.voice();
}
}*/
/*
class Usb{
private int number=100;
*/
/*//*
/可以添加任意访问修饰符(public,protected,默认,private),因为它的地位是一个成员
class Usb1{//成员内部类
public void say(){
//可以直接访问外部类的所有成员,包含私有的
System.out.println("number="+number);
}
}
//外部类访问---创建对象再访问
public void test(){
Usb1 usb1=new Usb1();
usb1.say();
}
//方法,返回一个Usb实例
public Usb1 getUsb1(){
return new Usb1();
}*//*
static class Usb3{//静态内部类(static修饰)只能访问外部类的所有静态成员,但不能访问非静态成员
public void say(){
System.out.println("hi");
}
}
public void test1(){
Usb3 usb3=new Usb3();
usb3.say();
}
//方法,返回一个Usb3实例
public Usb3 getUsb3(){
return new Usb3();
}
public static Usb3 getUsb4(){
return new Usb3();
}
}
public class Demo1 {
public static void main(String[] args) {
*/
/*Usb usb=new Usb();
usb.test();
//外部其他类,使用成员内部类的两种方式
//第一种方法 usb.new Usb1(); 相当于new Usb1()当作是usb成员
Usb.Usb1 usb1=usb.new Usb1();
usb1.say();
//第二种方法 在外部类中,编写一个方法可以返回Usb1对象
Usb.Usb1 usb2=usb.getUsb1();
usb2.say();*//*
Usb usb=new Usb();
usb.test1();
//外部其他类,使用成员内部类的两种方式
//第一种方式:静态内部类可以通过类名直接访问
Usb.Usb3 usb3=new Usb.Usb3();
usb3.say();
//编写一个方法,可以返回静态内部类实例对象
Usb.Usb3 usb4=usb.getUsb3();
usb4.say();
Usb.Usb3 usb5=Usb.getUsb4();
usb5.say();
//内部类 定义在局部位置(方法块/代码块) 1.局部内部类 2.匿名内部类
定义在成员位置 1.成员内部类 2.静态内部类
}
}
*/
//季节是有限的几个值,只读不修改,这时我们需要一个新的设计理念---枚举类
//class Season{//类
// 使用enum关键字,就不能继承其他类了,以为enum会隐式继承Enum 但枚举类和其它类一样,可以实现接口
/*
enum Season{ // enum 替代 class
*/
/*//*
/3.在Season内部,直接创建固定对象 优化,加入final修饰符(将构造器私有化) 枚举对象名大写(常量命名规范)
public static final Season SPRING = new Season("春天");
public static final Season SUMMER = new Season("夏天");
public static final Season AUTUMN = new Season("秋天");
public static final Season WINTER = new Season("冬天");*//*
//多个常量 ,间隔 一定要写在最前面 WHAT() 也可以写成 WHAT
SPRING("春天"),SUMMER("夏天"),AUTUMN("秋天"),WINTER("冬天"),WHAT(),WHY;
private String name;
private Season(String name){//1.将构造器私有化 防止new
this.name=name;
}
Season() {//无参构造器
}
private String getName() { //2.去掉setXXX方法 防止属性被修改 (枚举对象值通常为只读)
return name;
}
*/
/*
Enum的toString()
public String toString(){
return name;
}
*//*
*/
/* @Override
public String toString() {
return "Season{" +
"name='" + name + '\'' +
'}';
}*//*
}
public class Demo1 {
public static void main(String[] args) {
System.out.println("1:"+Season.SPRING);
Season autumn=Season.AUTUMN;
//输出枚举对象的名字
System.out.println("2:"+autumn.name());
// ordinal() 输出该对象的次序
System.out.println("3:"+autumn.ordinal());
*/
/*//*
/ 从反编译看 values() 返回 Season[]
Season[] array=Season.values();
for(int i=0;i< array.length;i++){//普通for循环
System.out.println(array[i]);
}
System.out.println("=========");
for(Season season:array){//增强for循环
System.out.println(season);
}
int[] numbers={1,2,9};
for(int i:numbers){//增强for循环
System.out.println("i="+i);
}*//*
// valueOf 寻找字符串,字符串必须是已有的常量名,否则报异常
Season autumn1=Season.valueOf("AUTUMN");
System.out.println("autumn1="+autumn1);
System.out.println(autumn1==autumn);
// compareTo 比较两个枚举常量的编号
System.out.println(Season.AUTUMN.compareTo(Season.SPRING));
}
}
*/
/*
@Override 该注解只能用于方法 @interface 不是interface,是注解类 是jdk1.5之后加入的
@Target 是修饰注解的注解 称为元注解
如果写了@Override逐渐,编译器会去检查是否真的重写了父类的方法;的确重写了,则编译器通过,否则编译器报错
@Deprecated 修饰某个元素,表示该元素已过时 不推荐使用,但仍可以使用 @Deprecated作用可以做到新旧版本的兼容和过渡
修饰方法,类,字段,包,参数
@SuppressWarnings({""}) {""}可以显示你希望不显示的警告信息 抑制编译器警告 @SuppressWarnings({"unused","unchecked"})
@Retention 是指该注解可以保留多长时间
@Retention(RetentionPolicy.SOURCE) (编译器将注解记录在java源文件)
@Retention(RetentionPolicy.CLASS) (编译器将注解记录在class文件)
@Retention(RetentionPolicy.RUNTIME) (编译器将注解记录在class文件,当运行java程序,JVM会保留注解)
@Inherited 如果某个类被@Inherited修饰,则其子类自动具有该注解
*/
/*
interface Sub{
public double sub_(double number1,double number2);
}
class Counter{
public void start(Sub sub,double number1,double number2){
double result=sub.sub_(number1,number2);
System.out.println("计算的结果是result="+result);
}
}
public class Demo1 {
public static void main(String[] args) {
Counter counter=new Counter();
counter.start(new Sub(){
@Override
public double sub_(double number1, double number2) {
return number1+number2;
}
},10.10,100);
}
}
*/
/*interface Vehicles{
public void work();
}
class Horse implements Vehicles{
@Override
public void work() {
System.out.println("一般情况下,使用白龙马前进");
}
}
class Boat implements Vehicles{
@Override
public void work() {
System.out.println("拿东海老王八当船过河");
}
}
class VehiclesFactory{//创建交通工具工厂类
private static Horse horse=new Horse();
public static Horse getHorse(){//将方法做成static,不创建交通工具工厂类,也可以调用对象
return horse;//白龙马创建一次就可以了
}
public static Boat getBoat(){
return new Boat();
}
}
class Person{
private String name;
private Vehicles vehicles;
public Person(String name, Vehicles vehicles) {
this.name = name;
this.vehicles = vehicles;
};
public void passRiver(){
if(!(vehicles instanceof Boat)){
vehicles=VehiclesFactory.getBoat();
}
vehicles.work();
}
public void usually(){
if(!(vehicles instanceof Boat)){
vehicles=VehiclesFactory.getHorse();
}
vehicles.work();
}
}
public class Demo1 {
public static void main(String[] args) {
Person tang=new Person("唐僧",new Horse());
tang.passRiver();
tang.usually();
}
}*/
555
/**
* @author 耿世伟
* @version 1.0
*/
/*
程序执行中发生不正常情况称为异常(开发过程中语法错误和逻辑错误不是异常)
异常分为两类 1.Error(错误) Jvm虚拟机无法解决的严重错误 比如栈溢出,内存不足
2.Exception(分为运行异常和编译异常(发生在java源文件)) 一般性错误
编译异常是必须处置的异常;运行时异常可以不做处理,因为这类异常很常见,若全处理可能会对程序可读性和运行效率产生影响
*/
/*public class Demo2 {//运行异常
public static void main(String[] args) {
*//* int number1=100;
int number2=0;
//出现异常程序崩溃;这样的程序也不算致命的错误,导致整个程序崩溃
//java设计者,提供了一个叫 异常处理机制来解决问题 try-catch处理机制来解决(快捷键 ctrl+alt+t)
try {//代码可能有异常
int result=number1 / number2;
} *//**//*catch (NullPointerException e){
System.out.println("空指针异常="+e.getMessage());
}
catch (Exception e) {//当异常发生时,后面的代码不在执行,系统将异常封装为Exception对象e,传递给catch
// 如果没有发生异常catch代码块不执行
//可以有多个catch语句,要求子类异常在后,子类异常在前
e.printStackTrace();//在命令行打印异常信息在程序中出错的位置及原因
System.out.println(e.getMessage());//输出异常信息
}*//**//*finally{//如果没有finally,语法是通过的
//不管try代码块是否有异常发生,始终要执行finally;所以,通常将释放资源,关闭链接的代码放在finally
//也可以try-finally配合使用,这种方法相当于没有捕获异常,就是执行这块代码,不管有没有发生异常,都必须执行某个业务逻辑
System.out.println("业务逻辑");
}
System.out.println("程序正常执行");*//*
}
public void test1() throws FileNotFoundException,NullPointerException {// throws 将发生的异常抛出,交给调用者来处理,最顶级的处理者是JVM
//throws 后面的异常类型可以是方法中产生的异常处理,也可以是它的父类;后面也可以是异常列表
FileInputStream one=new FileInputStream("d://aa.txt");
}
}*/
/*class One{}
class Two extends One{}
class Three extends One{}
public class Demo2 {
public static void main(String[] args) {
One one=new Two();//向上转型
Two two=(Two) one;//向下转型
//Three three=(Three) two;//类型转换异常
String name1="1234";
int number1=Integer.parseInt(name1);//将字符串转化为数字
System.out.println(number1);
String name2="阿伟学java";
int number2=Integer.parseInt(name2);
System.out.println(number2);//数字格式不正确异常
//还有:空指针异常 数学运算异常 数组下标访问异常
}
}*/
/*
异常处理就是当异常发生时,对异常的处理方式
编译异常,程序中必须处理 try-catch 或者 throws
对于运行异常,程序中如果没有处理,默认就是throws的方式处理
*/
/*class Father{
public void method() throws RuntimeException{
}
}
class Son extends Father{
//子类重写父类的方法时,所抛出的异常类型和父类抛出的异常一致,要么为父类抛出异常类型的子类型
@Override
public void method() throws NullPointerException {
super.method();
}
}*/
/*自定义异常 如果继承Exception 属于编译异常
throws 异常处理的一种方式 位置在方法声明处 后面跟异常类型
throw 手动生成异常的关键字 位置在方法体中 后面跟异常对象
如果抛出的是运行异常,则不要求程序员显示处理,因为有默认的处理机制(通常把自定义异常做成运行时异常)
*/
/*class One extends RuntimeException{
public One(String message) {
super(message);
}
}
public class Demo2 {
public static void main(String[] args) {
int age=80;
if(!(age>=0 &&age<=100)){
throw new One("需要年龄在0-100之间");
}
System.out.println("你的年龄范围正确");
}
}*/
/* Throwable是 Java 语言中所有错误或异常的超类(Error Exception(RuntimeException ClassNotFoundException))
五大运行异常
1.NullPointerException 空指针异常
2.ArithmeticException 数学运算异常
3.ArrayIndexOutOfBoundException 数组下标越界异常
4.ClassCastException 类型转换异常
5.NumberFormatException 数字格式不正确异常[]
*/
/*
针对八种数据类型相应的引用类型--包装类(有了类的特点就可以调用类的方法)
boolean---> Boolean char--->Character
其他六种包装类的父类是Number byte--->Byte short--->Short int--->Integer long--->Long float--->Float double--->Double
true?new Integer(1):new Double(2.0) 返回结果是1.0 要把三元运算符看做一个整体
*/
//public class Demo2 {
//
// public static void main(String[] args) {
// //jdk5以前需要手动装箱(基本->引用)
// /*int number1=10;
// Integer integer=new Integer(number1);//装箱1
// Integer integer1=Integer.valueOf(number1);//装箱2
// //拆箱(引用->基本)
// int number2=integer.intValue();
//
// // jdk5以后自动装箱
// int number3=100;
// Integer integer2=number3;
// //拆箱
// int number4=integer2;*/
//
// //包装类(Integer)->String
// /*Integer number1=100;
// String str1=number1+"";//方式一
// String str2=number1.toString();//方式二
// String str3=String.valueOf(number1);//方式三
// //String->包装类(Integer)
// String str4="123";
// Integer integer=Integer.parseInt(str4);//使用到自动装箱
// Integer integer1=new Integer(str4);//构造器*/
//
// /* System.out.println(Integer.MAX_VALUE);//返回最大值
// System.out.println(Integer.MAX_VALUE);//返回最小值
//
// System.out.println(Character.isDigit('a'));//判断是不是数字
// System.out.println(Character.isLetter('a'));//判断是不是字母
// System.out.println(Character.isUpperCase('a'));//判断是不是大写
// System.out.println(Character.isLowerCase('a'));//判断是不是小写
//
// System.out.println(Character.isWhitespace('a'));//判断是不是空格
// System.out.println(Character.toUpperCase('a'));//转成大写
// System.out.println(Character.toLowerCase('A'));//转成小写*/
//
// // == 基本类型,判断值是否相等
//
// /*
//
// 字符串的字符使用Unicode字符编码,一个字符(不管是字母还是汉字)占两个字节
// String 实现了Serializable,说明了字符串可以串行化(串行化:可以在网络传输);实现了Comparable,说明字符串可以比较
// String是final类,不能被其他类继承
//
// */
// /*final char[] value={'a','b','c'};
String有属性 private final char value[] ; value[]用于存放字符串内容(value是final类型,不可以修改,即value不能指向新的地址,但是单个字符串内容是可以变化的)
// value[0]='A';*/
//
// /*//创建String对象的区别
// String str1="hello";//方式一
// //先看常量池是否有"hello"数据空间,有就直接指向;如果没有重新创建,str1指向常量池的空间地址
// String str2=new String("hello");
// //现在堆中创建空间,里面维护了value属性,指向常量池的"hello"空间,如果常量池没有"hello",重新创建;如果有,直接通过value指向*/
//
// /*String str1="hello"+"Java";
// //编译器不傻,做了优化 String str1="helloJava"; 只创建了一个对象*/
//
// /*String str1="hello";
// String str2="Java";
// String str3=str1+str2;//最终str3指向堆中的对象(String) value[] -> 池中"helloJava"
// String str4="helloJava";
// System.out.println(str3==str4);//F*/
//
// /* System.out.println("阿伟已经死了".length());//获取字符串的长度 6
//
// // indexOf 获取字符在字符串第一次出现的索引,找不到返回-1
// String str1="qq.com";
// int index=str1.indexOf('.');//2
// System.out.println(index);
// System.out.println(str1.indexOf("co"));//3
// str1="999@qq.com";
// int index1=str1.lastIndexOf('@');
// System.out.println(index1);//3
//
// // substring 截取指定范围的字串
// String name="罗罗诺亚·索隆";
// System.out.println(name.substring(5));//从索引5的开始截取后面所有内容
// System.out.println(name.substring(5,7));//索隆*/
//
// /*String str1="heLLo";
// System.out.println(str1.toUpperCase());//转大写
// System.out.println(str1.toLowerCase());//转小写*/
//
// //concat 拼接字符串
// /*String str1="阿伟";
// String str2=str1.concat("已经").concat("死了");
// System.out.println(str1);
// System.out.println(str2);*/
//
// // replace 替换字符串字符
// /*String say="你,已经死了,不要再找了";
// String say1=say.replace("你","阿伟");
// System.out.println(say);
// System.out.println(say1);*/
//
// //split 分割字符
// /*String quatation="背后的伤痕是剑士的耻辱,索隆大大";
// String[] array=quatation.split(",");
// for(String string:array){//for(数据类型 变量名 :遍历的目标)
// System.out.println(string);
// }*/
//
// // toCharArray 转换为字符数组
// /*String str1="hello";
// char[] chars=str1.toCharArray();
// for(char char1:chars){
// System.out.println(char1);
// }*/
//
// // compareTo比较两个字符串的大小 长度相同,每个字符相等,返回0 长度不相等,前面字符相等,就返回两个字符串的差值
// /*String str1="hel";
// String str2="hello";
// System.out.println(str1.compareTo(str2)); //-2*/
//
// /*String name="阿伟";
// char gender='男';
// int age=18;
// String str1=String.format("我叫%s,性别%c,年龄%d,希望大家可以喜欢我!",name,gender,age);
// System.out.println(str1);
// String str2="我叫%s,性别%c,年龄%d,希望大家可以喜欢我!";
// String str3=String.format(str2,name,gender,age);
// System.out.println(str3);
// System.out.println(String.format(str2,name,gender,age));
// // %.2f 保留小数点两位,并进行四舍五入的处理 占位符(这些占位由后面变量替换)*/
//
// /*
// // String类是保存字符串常量的,每次更新都需要重新开辟空间,效率较低
// 因此java设计者还提供了StringBuilder和StringBuffer来增强String功能,提高效率
//
// StringBuffer代表可见的字符序列,可以对字符串内容进行增删(很多方法和String相同)
// StringBuffer(是一个final类,不能被继承)直接父类AbstractStringBuilder(父类有属性 char[]value ,不是final ,value存放字符串内容,放在堆中)
// StringBuffer实现了SeriaLizable(他的对象可以串行化)
// StringBuffer保存的是字符串常量,里面的值不可更改,每次更新实际上更新内容,而不是地址
// */
//
// /*//1.创建一个大小为16的char[],用于存放字符内容
// StringBuffer stringBuffer = new StringBuffer();
// //2.通过构造器指定char[]大小
// StringBuffer stringBuffer1=new StringBuffer(100);
// //3. char[]大小是 stringBuffer2.length()+16
// StringBuffer stringBuffer2=new StringBuffer("hello");
//
// // String->StringBuffer
// String str="hello";
// //方式一:构造器
// StringBuffer stringBuffer3=new StringBuffer(str);
// //方式二:使用append方法
// StringBuffer stringBuffer4=new StringBuffer();
// stringBuffer4=stringBuffer4.append(str);
//
// // StringBuffer-->String
// StringBuffer stringBuffer5=new StringBuffer("阿伟学Java");
// //方式一 使用StringBuffer提供的toString方法
// String str1=stringBuffer5.toString();
// //方式二 使用构造器来搞定
// String str2=new String(stringBuffer5);*/
//
// /*StringBuffer stringBuffer=new StringBuffer("hello");
//
// //append增
// stringBuffer.append(",");
// stringBuffer.append(100);
// stringBuffer.append(0.1);
// System.out.println(stringBuffer);
//
// //delete删 删除左闭右开
// stringBuffer.delete(5,12);
// System.out.println(stringBuffer);
//
// //查 找不到返回-1
// int indexOf=stringBuffer.indexOf("l");
// System.out.println(indexOf);
//
// //改 左闭右开
// stringBuffer.replace(1,2,"aha");
// System.out.println(stringBuffer);
//
// //插入 在索引0的位置插入
// stringBuffer.insert(0,"say:");
// System.out.println(stringBuffer);
//
// //长度
// System.out.println(stringBuffer.length());*/
//
// //打印价格的小数点前面每三位逗号隔开 3,542.88
// /*String price="3542.88";
// StringBuffer stringBuffer=new StringBuffer(price);
// for(int i=stringBuffer.lastIndexOf(".")-3;i>0;i-=3){
// stringBuffer.insert(i,",");
// }
// System.out.println(stringBuffer);*/
//
// /*StringBuilder(最快) ,没有做互斥处理(没有synchronized关键字)因此在单线程的情况下使用(字符串存在大量修改操作,单线程使用这个)
// StringBuffer(次之) ,线程安全(字符串存在大量修改操作,多线程使用这个)
// String(最慢),效率低但复用性高(很少修改,被多个对象引用,比如配置信息用它)
// */
//
// // Math基本数据运算的方法
//
// //abs绝对值
// /*System.out.println(Math.abs(-10));
//
// //pow求幂
// System.out.println(Math.pow(-2,3));
//
// //ceil 向上取整
// System.out.println(Math.ceil(-3.22));
//
// //floor 向下取整
// System.out.println(Math.floor(-3.21));
//
// //round 四舍五入
// System.out.println(Math.round(-3.54));
//
// //sqrt 开平方
// System.out.println(Math.sqrt(9.0));//负数 就会打印 NaN(not a number)
//
// //random随机数 [0,1)的数字 (int)(a+Math.random()*(b-a+1)) 打印2-7的数字 a就等于2,b等于7
// for(int i=1;i<10;i++){
// System.out.println((int)(2+Math.random()*(7-2+1)));
// }
//
// //max min 返回最大值最小值
// System.out.println(Math.max(5,4));
// System.out.println(Math.min(3,2));*/
//
// // Arrays类包含了一系列静态方法
//
// /* //1. toString返回数组的字符串形式
// int[] array={1,4,3,6,5};
// //System.out.println(Arrays.toString(array));
//
// //2. sort自然排序和定制排序
// Arrays.sort(array);// 自然排序 //数组是引用类型,通过sort排序后会影响实参
// System.out.println(Arrays.toString(array));*/
//
// //定制排序
// /*Integer array[]={1,3,5,9,7};
// Arrays.sort( array,new Comparator(){
// @Override
// public int compare(Object o1,Object o2){// public int compare返回值大于零或等于零会影响排序效果
// Integer number1=(Integer) o1;
// Integer number2=(Integer) o2;
// return number2-number1;
// }
// });
// System.out.println(Arrays.toString(array));
// */
//
// /* int array[]={1,-1,8,0};
// bubble(array, new Comparator() {
// @Override
// public int compare(Object o1, Object o2) {
// int number1=(Integer)o1;
// int number2=(Integer)o2;
// return number1-number2;//升序
// }
// });
// System.out.println(Arrays.toString(array));*/
//
// /*// binarySearch二分查找 如果数组不存在该元素 就返回 -(low + 1)
// Integer[] array={1, 2, 3, 7, 8, 9};//二分查找必须排好
// int index= Arrays.binarySearch(array,4);
// System.out.println("index="+index);
//
// // copyOf 在array数组中,拷贝array.length个元素到newArray
// Integer[] newArray=Arrays.copyOf(array,array.length);
// System.out.println(Arrays.toString(newArray));
// Integer[] newArray1=Arrays.copyOf(array,array.length+1);//多一个元素为null
// System.out.println(Arrays.toString(newArray));
// Integer[] newArray2=Arrays.copyOf(array,array.length-1);//少拷贝一个元素
// System.out.println(Arrays.toString(newArray));
//
// //equals 比较数组两个元素是否相等
// Integer[] array1={1,2,3,7,8};
// boolean equals=Arrays.equals(array,array1);
// System.out.println(equals);//数组元素一样返回true 否则false*/
//
// /*// asList将一组值转换为List集合
// List asList= Arrays.asList(3,2,6,5,9,8);
// System.out.println("asList="+asList);
// System.out.println(asList.getClass());// asList运行内存class java.util.Arrays$ArrayList是Arrays类的静态内部类*/
//
// Book[] books=new Book[3];
// books[0]=new Book("肖申克的救赎",99.99);
// books[1]=new Book("红楼梦",88.88);
// books[2]=new Book("三体",110.11);
//
// //按价格排序
// /*Arrays.sort(books, new Comparator() {
// @Override
// public int compare(Object o1, Object o2) {
// Book book1=(Book)o1;
// Book book2=(Book)o2;
// double sub=book2.getPrice()- book1.getPrice();
// if(sub>0){
// return 1;
// }
// else if(sub<0){
// return -1;
// }
// else{
// return 0;
// }
// }
// });*/
//
// Arrays.sort(books, new Comparator<Book>() {
// @Override
// public int compare(Book o1, Book o2) {
// Book book1=(Book) o1;
// Book book2=(Book) o2;
// return book2.getName().length()-book1.getName().length();
//
// }
// });
//
// System.out.println(books[0]);
// System.out.println(Arrays.toString(books));
//
// }
// public static void bubble(int[] array, Comparator c){
// //冒泡+排序
// int temp=0;
// for(int i=0;i<array.length;i++){
// for(int j=0;j<array.length-1;j++){
// if(c.compare(array[j],array[j+1])>0){
// temp=array[j];
// array[j]=array[j+1];
// array[j+1]=temp;
// }
// }
// }
//
// }
//}
//
//class Book{
// private String name;
// private double price;
//
// public Book(String name, double price) {
// this.name = name;
// this.price = price;
// }
//
// public String getName() {
// return name;
// }
//
// public void setName(String name) {
// this.name = name;
// }
//
// public double getPrice() {
// return price;
// }
//
// public void setPrice(double price) {
// this.price = price;
// }
//
// @Override
// public String toString() {
// return "Book{" +
// "name='" + name + '\'' +
// ", price=" + price +
// '}';
// }
//}
/*import java.text.ParseException;
//@SuppressWarnings("all")
public class Demo2 {
public static void main(String[] args) throws ParseException {*/
//System类的常见方法
//exit退出当前程序
/*System.out.println("1");
System.exit(0); // exit(0) 表示程序退出,0表示正常的状态
System.out.println("2");*/
//arraycopy复制数组元素
/* int[] array={1, 2, 3};
int[] array1=new int[3];
System.arraycopy(array,0,array1,0,2); // array源数组 0:源数组索引值 array1目标数组 0:目标索引 3:拷贝长度
System.out.println("array1="+ Arrays.toString(array1));*/
//System.gc();运行垃圾回收机制
//currentTimeMillis() 返回当前时间距离1970-1-1的毫秒数
//System.out.println(System.currentTimeMillis());
//BigInteger适合保存较大的整形 BigDecimal适合保存精度更高的浮点型(小数)
/*BigInteger bigInteger=new BigInteger("589999999999999999999999999999999999999999999999999");
BigInteger bigInteger1=new BigInteger("1");
System.out.println(bigInteger);
//在对BigInteger进行加减乘除,需要使用相应的方法,不能直接进行 + - * /
BigInteger add=bigInteger.add(bigInteger1);
System.out.println(add);
BigInteger subtract=bigInteger.subtract(bigInteger1);
System.out.println(subtract);
BigInteger multiply=bigInteger.multiply(bigInteger1);
System.out.println(multiply);
BigInteger divide=bigInteger.divide(bigInteger1);
System.out.println(divide);*/
/*BigDecimal bigDecimal=new BigDecimal("1.999999999999999999999999999999999999999999999998");
System.out.println(bigDecimal);
BigDecimal bigDecimal1=new BigDecimal(0.2);
System.out.println(bigDecimal.add(bigDecimal1));
System.out.println(bigDecimal.subtract(bigDecimal1));
System.out.println(bigDecimal.multiply(bigDecimal1));
//System.out.println(bigDecimal.divide(bigDecimal1));// 可能抛出异常 bigDecimal对应精度太高,除不尽
System.out.println(bigDecimal.divide(bigDecimal1,BigDecimal.ROUND_CEILING));//如果有无限循环的小数,就会保留分子的精度
System.out.println(bigDecimal.divide(bigDecimal1));*/
/* //第一代日期类 JDK1.0包含了Date类,但它的大多数方法已经在JDK1.1中引用
Date date=new Date();//获取当前系统时间
System.out.println("当前日期="+date);//默认输出的日期格式是国外的格式,因此通常需要对格式进行转换
SimpleDateFormat sdf=new SimpleDateFormat("yyyy年MM月dd日 hh:mm:ss E");//指定相应的日期格式
String format=sdf.format(date);// format将日期转换成指定格式的字符串
System.out.println("当前日期="+format);
//可以把格式化的String,转化为Date
String str="1998年01月01日 10:10:10 星期四";
Date parse=sdf.parse(str);//使用的std格式需要你给的String的格式一样,否则会抛出异常
System.out.println(sdf.format(parse));*/
/*//第二代日期类 Calendar是一个抽象类,构造器是private 可以通过getInstance来获取实例
Calendar calendar=Calendar.getInstance(); //创建日历对象 比较简单自由
System.out.println(calendar);
System.out.println("年:"+calendar.get(Calendar.YEAR));
System.out.println("月:"+calendar.get(Calendar.MONTH));
System.out.println("日:"+calendar.get(Calendar.DAY_OF_MONTH));
System.out.println("小时:"+calendar.get(Calendar.HOUR));
System.out.println("分钟:"+calendar.get(Calendar.MINUTE));
System.out.println("每秒:"+calendar.get(Calendar.SECOND));
// Calendar没有专门格式化的方法,所以需要程序员自己来组合
System.out.println(calendar.get(Calendar.YEAR)+"年"+calendar.get(Calendar.MONTH)+"月"+calendar.get(Calendar.DAY_OF_MONTH)+"日");
//如果我们需要24进制来获取时间 Calendar.MOTH 改成 Calendar.HOUR_OF_DAY
System.out.println("小时:"+calendar.get(Calendar.HOUR_OF_DAY));*/
/*前两代不足分析:
可变性:日期和时间这样的类应该不可变的
偏移性:Date中的年份从1900开始,而月份是从0开始的
格式化:格式化只对Date有用,Calendar则不行
此外:他们还有线性安全
//第三代日期常见方法 LocalDate(日期) LocalTime(时间) LocalDateTime(日期+时间) JDk8加入
*/
/* LocalDateTime ldt=LocalDateTime.now();// now()返回当前的日期和对象
System.out.println(ldt);
//使用DateTimeFormatter对象进行格式化
DateTimeFormatter dateTimeFormatter=DateTimeFormatter.ofPattern("yyyy-MM-dd HH:mm:ss");
String format=dateTimeFormatter.format(ldt);
System.out.println("格式化日期"+format);
System.out.println("年"+ldt.getYear());
System.out.println("月"+ldt.getMonth());
System.out.println("日"+ldt.getDayOfMonth());
System.out.println("时"+ldt.getHour());
System.out.println("分"+ldt.getMinute());
System.out.println("秒"+ldt.getSecond());
//通过plus 和 minus方法可以对当前时间进行加和减
LocalDateTime localDateTime=ldt.plusDays(365);// 365天后是什么时候
System.out.println("365天后ldt值为"+dateTimeFormatter.format(localDateTime));
LocalDateTime localDateTime1=ldt.minusDays(365); // 365天前是什么时候
System.out.println("365天后ldt值为"+dateTimeFormatter.format(localDateTime1));*/
/* //instant 时间戳
Instant now =Instant.now();//通过静态now获取当前时间戳的对象
System.out.println(now);
//通过from可以把Instant转成Date
Date date=Date.from(now);
System.out.println(date);
//通过date的toInstant()可以把date转换为Instant对象
Instant instant=date.toInstant();
System.out.println(instant);*/
//将字符串部分进行反转
/*String str=null;
try {
str = reverse(str, 1, 5);
} catch (Exception e) {
System.out.println(e.getMessage());
return;
}
System.out.println("==交换前==");
System.out.println(str);
System.out.println("==交换后==");
System.out.println(str);*/
/* //输入用户名,密码,邮箱,若果格式正确则提示注册成功,否则生成异常
String name="awei";
String password="123456";
String email="aweo@qq.com";
try {
user(name,password,email);
System.out.println("恭喜你,注册成功~");
} catch (Exception e) {
System.out.println(e.getMessage());
}
}
public static String reverse(String str,int start,int end){
if(!(str!=null&&start>=0&&end>start&&end<str.length())){//验证 写出正确的然后取反 过关斩将
throw new RuntimeException("参数不正确");
}
char[] chars=str.toCharArray();
char temp=' ';
for(int i=start,j=end;i<j;i++,j--){
temp=chars[i];
chars[i]=chars[j];
chars[j]=temp;
}
return new String(chars);//使用chars重新构建String返回即可
}
public static void user(String name,String password,String email){
if(!(name!=null&&password!=null&&email!=null)){
throw new RuntimeException("参数不能为null");
}
//第一关
if(!(name.length()>=2&&name.length()<=4)){
throw new RuntimeException("用户名长度为2-4");
}
//第二关
if(!(password.length()==6&&isDigital(password))){
throw new RuntimeException("密码长度为6,并且是数字");
}
//第三关
int index=email.indexOf('@');
int index1=email.indexOf('.');
if(!(index>0&&index1>index)){
throw new RuntimeException("邮箱需要有 @ 和 . ");
}
}
public static boolean isDigital(String str){
char[] chars=str.toCharArray();
for (int i = 0; i <chars.length ; i++) {
if(chars[i]<'0'||chars[i]>'9'){
return false;
}
}
return true;
}
}
*/
//数组:长度开始时必须指定,而且一旦指定,不能修改,保存的必须是同一类型-->集合
/*public class Demo2 {
public static void main(String[] args) {*/
//集合分为两种 (单列集合和双列集合) List Set 接口实现子类是单列集合 Map接口实现子类是双列集合
/*ArrayList arrayList =new ArrayList();
arrayList.add("jack");
arrayList.add("tom");
HashMap hashMap=new HashMap();
hashMap.put("N1","haha");
hashMap.put("N2","hehe");*/
/*List list=new ArrayList();
list.add("awei");
list.add(10);//相当于 list.add(new Integer(10))
list.add(true);
System.out.println(list);
//remove 删除指定元素
//list.remove(0);//索引值删除
list.remove("awei");//元素删除
System.out.println(list);
//contains:查找元素是否存在
System.out.println(list.contains("awei"));//不存在false
//size获取元素个数
System.out.println(list.size());
//isEmpty 判断是否为空
System.out.println(list.isEmpty());//F
*/
/*//clear 清空
list.clear();
System.out.println(list);
//addAll 添加多个元素
ArrayList list1=new ArrayList();
list1.add("haha");
list1.add("hehe");
list.addAll(list1);
System.out.println(list);
//containsAll 查找多个元素是否都存在
System.out.println(list.containsAll(list1));//T
//removeAll 删除多个元素
list.removeAll(list1);
System.out.println(list);*/
/*Iterator(迭代器) 主要遍历Collection集合中的元素
所有实现Collection接口的集合都有一个iterator()方法,用于返回一个实现了Iterator接口的对象,即返回一个迭代器
迭代器的执行原理: hasNext()//判断是否还有下一个元素 next()//指针下移到下一个集合位置
在调用it.next()方法之前必须调用it.hasNext()进行检测,若不调用,并且下一条记录无效,直接调用it.next()会抛出异常
*/
/* Collection collection=new ArrayList();
collection.add(new Book("红楼梦",55.55));
collection.add(new Book("水浒传",66.66));
//System.out.println(collection);
//遍历collection集合
// 1.先找到collection对应的迭代器
Iterator iterator =collection.iterator();
// 2.使用while循环遍历
while (iterator.hasNext()) {//判断是否还有数据 生成while快捷键 itit 显示所有快捷键 ctrl + j
Object next = iterator.next();//返回下一个元素,类型是Object
System.out.println(collection);
}
//3.当退出while循环 这时iterator迭代器指向最后一个元素
//iterator.next();
//4.如果再次遍历 需要重置我们的迭代器
iterator =collection.iterator();
while(iterator.hasNext()){
Object obj=iterator.next();
System.out.println(obj);
}*/
/*
//增强for(底层仍然是迭代器)循环就是简化版的iterator,本质一样,只能用于遍历数组和集合 快捷方式I
List list=new ArrayList();//ArrayList线程不安全(执行效率高)
list.add("haha");
list.add("hehe");
System.out.println(list);
//list 集合每个元素都有对应的索引,即支持索引
System.out.println(list.get(0));
//在索引1处插入对象 nihao
list.add(1,"nihao");
System.out.println(list);
List list1=new ArrayList();
list1.add("baga");
list1.add("baba");
//把list1的对象全部加到list
list.addAll(1,list1);
System.out.println(list);
list1.addAll(1,list);
//返回obj在当前集合首次出现的位置
System.out.println(list.indexOf("haha"));
list.add("haha");
System.out.println(list.lastIndexOf("haha"));
//移除index位置的元素,并返回元素
list.remove(0);
System.out.println(list);
//替换index的元素
list.set(0,"haha");
System.out.println(list);
//返回子集合 左闭右开
List returnList=list.subList(0,2);
System.out.println(returnList);
//遍历ArrayList LinkedList Vector
for (int i=0;i<list.size();i++) {
*//*Object object=list.get(i);
System.out.println(object);*//*
System.out.println(list.get(i));
}
list.add(null);//可以存放空指针
System.out.println(list);*/
/*
ArrayList是由数组来实现数据存储的 如果使用无参构造器,则初始elementDate容量为0(jdk7是10);
添加元素先看是否需要扩容,需要则调用grow方法 第一次扩容是10,再次扩容每次是1.5倍
new ArrayList(100) 如果使用有参构造器,初始为100,后面扩容每次是1.5倍
transient 表示瞬间,短暂的,表示该属性不会被序列号 //一个序列化后的对象 可以被写到数据库或文件中,也可用于 网络传输
Vector底层也是一个对象数组(线程同步即线程安全) 如果无参,默认10,满后按两倍扩容 指定大小也是后面两倍扩容
LinkedList(线程不安全)底层维护了一个双向列表 维护了两个属性first(指向首节点)和last(指向尾节点)
每个节点又维护了prev(指向前一个节点) next(指向后一个节点) item三个属性 最终实现了双向链表
LinkedList的元素添加和删除,不是通过数组完成,相对来说效率较高
*/
/*//模拟实现一个简单的双向链表
Node jack=new Node("jack");
Node tom=new Node("tom");
Node awei=new Node("awei");
//连接3个节点,形成双向链表 jack->tom->awei
jack.next=tom;
tom.next=awei;
//awei->tom->jack
awei.prev =tom;
tom.prev =jack;
Node first=jack;//让first引用指向jack;就是双向链表的头节点
Node last=awei;//让last引用指向awei,这就是双向链表的尾节点
//从头到尾遍历
while(true){
if(first==null){
break;
}
//输出first信息
System.out.println(first);
first=first.next;
}
//从尾到头遍历
*//*while(true){
if(last==null){
break;
}
System.out.println(last);
last=last.prev;
}*//*
//创建一个节点
Node laoliu=new Node("laoliu");
laoliu.next=awei;
laoliu.prev=tom;
tom.next=laoliu;
awei.prev=laoliu;
//让first再次指向jack
System.out.println("============");
first=jack;
while(true){
if(first==null){
break;
}
System.out.println(first);
first=first.next;
}*/
/* LinkedList linkedList=new LinkedList();
linkedList.add(1);
linkedList.add(2);
linkedList.add(3);
System.out.println(linkedList);
//删除一个节点
linkedList.remove();//默认删除第一个
System.out.println(linkedList);
linkedList.remove(1);
System.out.println(linkedList);
//修改某个节点对象
linkedList.set(0,99);
System.out.println(linkedList);
//得到某个节点对象 get()
System.out.println(linkedList.get(0));
linkedList.add(55);
linkedList.add(44);
//因为LinkedList实现了List接口,遍历方式也有三种
System.out.println("==================");
Iterator iterator=linkedList.iterator();
while(iterator.hasNext()){
Object obj=iterator.next();
System.out.println(obj);
}
System.out.println("==================");
for(Object o1:linkedList){
System.out.println(o1);
}
System.out.println("==================");
for(int i=0;i<linkedList.size();i++){
System.out.println(linkedList.get(i));
}*/
//增删操作多选择LinkedList 查该操作多选择ArrayList(查改效率比较高)
/*
Set接口基本介绍 无序(添加和取出的顺序不一样),没有索引 不允许有重复的元素,最多包含一个null
跟List接口一样,Set接口也是Collection的子接口,因此常用方法和Collection一样(不能用索引的方式来遍历数组)
*/
/*Set set=new HashSet();
set.add("jack");
set.add("hello");
set.add("jack");//只会显示一次
set.add("haha");
System.out.println(set);
set.remove("hello");//删除
System.out.println(set);
//迭代器
Iterator iterator=set.iterator();
while(iterator.hasNext()){
Object obj=iterator.next();
System.out.println(obj);
}
System.out.println("======");
for(Object obj:set){
System.out.println(obj);
}*/
// HashSet(实际上是HashMap)实现了set接口 可以存放null值(但只能有一个) 不能有重复元素
// HashSet底层是HashMap 添加一个元素,先得到hash值,会转成索引值 找到存储数据表table,看这个索引位置是否已经存在元素
//如果没有直接加入,如果有,调用equals比较,如果相同就放弃添加,不同则添加到最后
//HashSet第一次添加,数组table扩容到16,临界值是16*0.75 如果数组使用到了临界值12,则就会扩容到32,新的临界值32*0.75
//在Java8中,如果一个链条的元素个数是8,并且table>=64,就会进行树化(红黑树),否则仍然采用数组扩容机制
//HashMap底层是数组+链表+红黑树
/* Set hashSet=new HashSet();
hashSet.add(null);
hashSet.add(null);
hashSet.add(123);
System.out.println(hashSet);
System.out.println(hashSet.add("join"));//在执行add方法后,会返回一个boolean值 添加成功true
System.out.println(hashSet.add(123));//F
hashSet.remove("null");
System.out.println(hashSet);
//经典面试题
System.out.println(hashSet.add(new String("haha")));//T
System.out.println(hashSet.add(new String("haha")));//F*/
// 调试debug 就完了
/*Node1[] table=new Node1[16];//数组类型是Node1[] 有些人直接把Node[]数组称为表
System.out.println(table);
Node1 aWei=new Node1("aWei",null);
table[2]=aWei;
Node1 rose=new Node1("rose",null);
aWei.next=rose;//将rose节点挂载到aWei
Node1 jack=new Node1("jack",null);
System.out.println(table);*/
//定义一个Person类,当name和age的值相等,认为是相同的类,不能添加到HashSet集合中
/*Set set=new HashSet();
set.add(new Person("haha",18));
set.add(new Person("haha",19));
set.add(new Person("haha",18));
System.out.println(set);*/
//LinkedHashSet(底层是一个LinkHashMap 底层维护了一个数组(hash表)+双向链表(head和tail))是HashSet的子类 同时也不允许添加元素 遍历LinkedHashSet也能确保插入顺序和遍历顺序一样
//第一次添加时,数组扩容到16 ,数组是HashMap$Node[] 存放节点类型/存放的元素LinkedHashMap$Entry
/*
JDk8 Map接口特点 用于保存具有映射关系的数据Key(不可以重复)-Value(可以重复)
Map中的key和value可以是任何应用数据的类型,会封装到HashMap$Node对象中(HashMap$Node存放到entrySet就方便我们便利,因为Map.Entry提供了重要方法 K-getKey() V-getValue() )
k-v为了方便遍历,还会创建EntrySet集合,该集合存放的元素类型Entry,而一个Entry对象就有一个k-v
Map接口常用的实现类:HashMap(是Map接口频率使用最高的,线程不安全) Hashtable 和Properties
*/
/* Map map=new HashMap();
map.put("first","古力娜扎");//常用String类作为Map的key
map.put("first","马儿扎哈");//当有相同的key 就等价于替换
map.put(null,null);
map.put(null,"hello");// key为null只能有一个 value为null可以为多个
map.put("second","雷霆嘎巴");*/
/* System.out.println(map);
// System.out.println(map.get(null));// 通过get方法,传入key,会返回对应的value
//remove 根据键删除映射关系
map.remove("first");
System.out.println(map);
//size 获取元素个数
System.out.println(map.size());
//isEmpty:判断个数是否为零
System.out.println(map.isEmpty());//F
//containsKey 查找键是否存在
System.out.println(map.containsKey("awei"));//F
//clear 清楚k-v
map.clear();
System.out.println(map);*/
//Map接口遍历方法
/*//1.先取出所有的Key 通过key 取出对应的Value
Set keyset=map.keySet();//获取所有键
//增强for
for(Object key:keyset){
System.out.println(key+"-"+map.get(key));
}
//迭代器
System.out.println("-----------");
Iterator iterator=keyset.iterator();
while(iterator.hasNext()){
Object key=iterator.next();
System.out.println(key+"-"+map.get(key));
}*/
/*//2.把所有的values取出
Collection values=map.values();
for (Object value :values) {
System.out.println(value);
}
System.out.println("-------------");
//迭代器
Iterator iterator=values.iterator();
while(iterator.hasNext()){
Object value=iterator.next();
System.out.println(value);
}*/
//3.通过EntrySet 来获取k-v
/* Set entrySet=map.entrySet();
for (Object entry :entrySet) {
//将entry转换Map.Entry
Map.Entry map1=(Map.Entry)entry;
System.out.println(map1.getKey()+"-"+map1.getValue());
}
//迭代器
System.out.println("--------------");
Iterator iterator=entrySet.iterator();
while (iterator.hasNext()) {
Object next = iterator.next();
//System.out.println(next.getClass());//HashMap$Node实现Map.Entry(getKey getValue)
Map.Entry map2=(Map.Entry)next;
System.out.println(map2.getKey()+"-"+map2.getValue());
}*/
/* Map hashMap=new HashMap();
//添加对象
hashMap.put(1,new Person("awei",18222));
hashMap.put(2,new Person("rose",17222));
hashMap.put(3,new Person("jack",19222));
//遍历一
Set keySet=hashMap.keySet();
for (Object key :keySet) {
Person person=(Person)hashMap.get(key);
if(person.getPrice()>18000){
System.out.println(person);
}
}
//遍历二
Set entrySet=hashMap.entrySet();
Iterator iterator= entrySet.iterator();
while(iterator.hasNext()){
Map.Entry entry=(Map.Entry)iterator.next();
Person person=(Person)entry.getValue();
if(person.getPrice()>18000){
System.out.println(person);
}
}
*/
/*JDK7 hashMap(底层维护了Node类型的数组table)实现了数组+链表 JDK8实现了数组+链表+红黑树
当创建对象时,加载因子是0.75 添加对象,通过key哈希值得到在table的索引,然后是否判断索引是否有该元素,有元素则判断是否和加入的元素相等
相等直接替换,如果不相等则判断树结构还是链表结构,做出相应处理,容量不够就会扩容(第一次默认16)(后面扩容为原容量的两倍)
HashTable存放的元素键值对 K-V 键和值都不能为null ; 线程是安全的(效率较低) ;HashMap(效率高)线程不安全;初始大小为11;乘2加1扩容
Properties类继承Hashtable并实现了Map,也是使用一种健值的形式来存储数据 还可以读取和修改xxx.properties文件
如果有相同的key,value被替换
*/
/* Properties properties=new Properties();
properties.put("jack",100);// k-v
//properties.put(null,88);//空指针异常
properties.put("smith",200);
properties.put("awei",300);
System.out.println(properties);
System.out.println(properties.get("awei"));
//删除
properties.remove("smith");
System.out.println(properties);
*/
/*
如何选择集合 先判断存储类型(一组对象或一组健值)
一组对象:Collection接口
允许重复List(增删多LinkedList底层维护了一个双向链表 改查多ArrayList底层维护了一个Object可变数组)
不允许重复Set(无序HashSet 数组+链表+红黑树底层HashMap,维护了一个哈希表 排序TreeSet) 插入和取出顺序一致LinkedHashSet维护数组+双向链表
一组健值: Map
健无序(HashMap底层哈希表 jdk7数组+链表 jdk8数组+链表+红黑树)
健排序(TreeMap)
健插入和取出一致:LinkedHashMap
读取文件Properties
*/
//TreeSet treeSet=new TreeSet();//无参构造创建TreeSet,仍然无需
/*TreeSet treeSet=new TreeSet(new Comparator() {
@Override
public int compare(Object o1, Object o2) {
//调用String的compareTo方法进行字符串大小比较
//return ((String)o1).compareTo((String)o2);
//加入的元素按照长度大小排序
return ((String)o1).length()-((String)o2).length();
}
});
treeSet.add("haha");
treeSet.add("ehe");
treeSet.add("nihao");
System.out.println(treeSet);*/
//TreeMap treeMap=new TreeMap();//TreeMap 使用无参构造器,也是无序的
/* TreeMap treeMap=new TreeMap(new Comparator(){
@Override
public int compare(Object o1, Object o2) {
//调用String的compareTo方法进行字符串大小比较
//return ((String)o1).compareTo((String)o2);
//加入的元素按照长度大小排序
return ((String)o1).length()-((String)o2).length();
}
});
treeMap.put("jac","haha");
treeMap.put("rose","gaga");
treeMap.put("ji","nihao");
System.out.println(treeMap);*/
//Collections工具类 是一个操作Set,List和Map等集合的工具类 提供了一序列的静态方法
/* List list=new ArrayList();
list.add("hahaha");
list.add("rose");
list.add("O");
list.add("gun");
list.add("gun");
//反转List中元素的顺序
Collections.reverse(list);
System.out.println(list);
//根据元素的自然顺序对指定List进行升序操作
Collections.sort(list);
System.out.println(list);
//按照字符串大小长度排序
Collections.sort(list,new Comparator(){
@Override
public int compare(Object o1, Object o2) {
return ((String)o1).length()-((String)o2).length();
}
});
//指定元素进行交换swap(list,int,int)
Collections.swap(list,0,1);
//根据元素的自然顺序,返回集合的最大元素
System.out.println(Collections.max(list));
//根据指定的顺序,返回最大的元素
Object max=Collections.max(list,new Comparator(){
@Override
public int compare(Object o1, Object o2) {
return ((String)o1).length()-((String)o2).length();
}
});
System.out.println(max);
// Object min(Collection) Objection(Collection,Comparator)
//返回指定元素出现的次数
System.out.println(Collections.frequency(list,"gun"));
ArrayList one=new ArrayList();
for(int i=0;i<list.size();i++){
one.add("");
}
//copy拷贝 需要两个集合size一样
Collections.copy(one,list);
System.out.println(one);
//新值换旧值
Collections.replaceAll(list,"gun","哦哦");
System.out.println(list);*/
/*
HashSet和TreeSet去重机制
HashSet:hashCode()+equals()先通过存入对象,进行运算得到hash值,通过hash值找到索引,如果table索引所在的位置
,没有数据,直接存放,如果有数据就进行equals遍历比较,比较后不相同添加,相同不添加
TreeSet:如果你传入了一个Comparator匿名对象,就使用实现的comparator去重,如果方法返回0,就认为是相同的元素,就不添加
,如果你没有传入Comparator匿名对象,则你添加的对象实现Comparable接口的compareTo去重
*/
/* TreeSet treeSet=new TreeSet();
// TreeSet()构造器没有传入Comparator接口的匿名内部类 所以底层就把Person转换Comparable类型
treeSet.add(new Person());//ClassCastException 类强制转换异常*/
/* }
}*/
//class Person{}
/*class Person implements Comparable{
@Override
public int compareTo(Object o) {
return 0;//如果方法返回0,就认为是相同的元素,就不添加
}
}*/
/*class Book{
private String name;
private double price;
public Book(String name, double price) {
this.name = name;
this.price = price;
}
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
public double getPrice() {
return price;
}
public void setPrice(double price) {
this.price = price;
}
@Override
public String toString() {
return "Book{" +
"name='" + name + '\'' +
", price=" + price +
'}';
}
}
class Node{
public Object item;//真正存放的数据
public Node next;//指向后一个节点
public Node prev;//指向前一个节点
public Node(Object name){
this.item=name;
}
@Override
public String toString() {
return "Node{" +
"name=" + item +
'}';
}
}*/
/*
class Node1{//节点 存储数据 可以指向下一个节点
Object item;//存放数据
Node1 next;//指向下一个节点
public Node1(Object item, Node1 next) {
this.item = item;
this.next = next;
}
public Object getItem() {
return item;
}
public void setItem(Object item) {
this.item = item;
}
public Node1 getNext() {
return next;
}
public void setNext(Node1 next) {
this.next = next;
}
@Override
public String toString() {
return "Node1{" +
"item=" + item +
", next=" + next +
'}';
}
}
*/
/*class Person{
private String name;
private int age;
public Person(String name, int age) {
this.name = name;
this.age = age;
}
@Override
public String toString() {
return "\n"+"Person{" +
"name='" + name + '\'' +
", age=" + age +
'}';
}
@Override
public boolean equals(Object o) {
if (this == o) return true;
if (o == null || getClass() != o.getClass()) return false;
Person person = (Person) o;
return age == person.age && Objects.equals(name, person.name);
}
@Override
public int hashCode() {
return Objects.hash(name, age);
}
}*/
/*class Person{//使用HashMap添加三个对象,并遍历大于18000的员工
private String name;
private double price;
public Person(String name, double price) {
this.name = name;
this.price = price;
}
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
public double getPrice() {
return price;
}
public void setPrice(double price) {
this.price = price;
}
@Override
public String toString() {
return "Person{" +
"name='" + name + '\'' +
", price=" + price +
'}';
}
}*/
666
/**
* @author 耿世伟
* @version 1.0
*/
/*public class Demo3 {
*//*
传统方法不能对ArrayList中的数据类型进行约束(不安全)
遍历的时候需要进行类型转换,如果数据特变多,就会影响效率
泛型(广泛的类型==>Integer,String等 Jdk5出现的)好处:编译的时候,检查元素类型,提高了安全性;减少了类型转换次数,提高了效率
Java泛型可以保证如果程序在编译时没有警告,运行时就不会发生ClassCastException异常 同时代码更加简洁,健壮
泛型的类型是在创建对象时确定的(因为创建对象,需要指定确定类型)
*//*
public static void main(String[] args) {*/
/* //ArrayList<Dog>表示存放ArrayList集合中的元素是Dog类型
ArrayList<Dog> arrayList=new ArrayList<Dog>();
arrayList.add(new Dog("旺财",18));
arrayList.add(new Dog("进宝",19));
//遍历的时候,直接取出Dog类型而不是Object
for(Dog dog:arrayList){
//不使用泛型 存放先转换成Object 再取出时还要转换成Dog
System.out.println(dog.getName()+"+"+dog.getAge());
}*/
//给泛型指定数据类型,要求是引用类型,而不是基本数据类型
/*Person<String> person=new Person<String>("招财");
Person<Integer> person1=new Person<Integer>(001);*/
/*//给泛型指定具体类型后,可以传入该类型或者子类型
Word<A> one=new Word<A>(new A());// A不代表值,而是类型 任何字母都可以,通常是T,是Type的缩写
Word<A> two=new Word<A>(new B());
//在实际开发中 也可以简写 编译器会进行类型推断
Word<A> two1=new Word<>(new B());*/
/* ArrayList arrayList=new ArrayList();
//在创建对象,没有指定类型,默认Object
//等价于 ArrayList<Object> arrayList=new ArrayList<>();*/
/* List<Object> list1=new ArrayList<>();
List<String> list2=new ArrayList<>();
List<AA> list3=new ArrayList<>();
List<BB> list4=new ArrayList<>();
List<CC> list5=new ArrayList<>();
//--------------------------
test(list1);
test(list2);
test(list3);
test(list4);
test(list5);
//----------------------------
*//*test1(list1);
test1(list2);*//*
test1(list3);
test1(list4);
test1(list5);
//----------------------------
test2(list1);
//test2(list2);
test2(list3);
*//*test2(list4);
test2(list5);*//*
}
public static void test(List<?>c){//支持任意泛型类型
}
public static void test1(List<?extends AA>c){//支持AA及AA的子类
}
public static void test2(List<?super AA>c){//支持AA及AA的父类
}
}*/
/*class AA{}
class BB extends AA{}
class CC extends BB{}*/
/*//Cat后面泛型 我们就把Cat称为自定义泛型
class Cat<A,B,C>{// A B C泛型标识符,一般是单个字母大写 泛型可以有很多个 泛型类
String name;
A a;
// static A a1; 静态和类相关,在类加载时,对象还没创建,静态方法使用泛型,JVM无法初始化,所以会报错
// 静态方法也不能使用泛型
B b;
C c;
A[] array;//泛型的数组不能被初始化 因为是泛型,不能确定A的类型,不知道要开辟多大空间
public <T,R>void hi(T t,A a){//泛型方法
}
public void say(B b){//不是泛型方法 而是使用了泛型
//泛型方法,可以定义在普通类中,也可以定义在泛型类
//当泛型方法被调用 类型会确定
}
}*/
/*//自定义泛型接口
interface A<B,C>{
}
//在继承接口 指定泛型接口的类型
interface A1 extends A<String,Integer>{
}
//在实现接口 指定泛型接口的类型 没有指定默认Object
class A2 implements A<Float,Double>{
}*/
/*class A{
public A() {
}
}
class B extends A{};
class Word<E>{
E e;
public Word(A a) {
}
}*/
/*class Dog{
private String name;
private int age;
public Dog(String name, int age) {
this.name = name;
this.age = age;
}
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
public int getAge() {
return age;
}
public void setAge(int age) {
this.age = age;
}
}*/
/*class Person<E>{//泛型作用 可以在类声明时
E name;//通过一个标识表示类中某个属性 该类型在定义Person类型指定
public Person(E name) {//通过一个标识表示类中参数类型
this.name = name;
}
public E getName() {//通过一个标识表示类中方法的返回值类型
return name;
}
public void setName(E name) {
this.name = name;
}
}*/
//一个类中有很多代码需要测试 为了测试需要写在main方法中 多次代码测试就需要来回注销,切换很麻烦
//如果可以直接运行一个方法,并给出相关信息,就好了 ------> JUnit
/*public class Demo3{
@Test
public void my(){
System.out.println(1+1);
}
}*/
/*
java绘图坐标系
像素是一个密度单位 而厘米是一个长度单位
*/
/*public class Demo3 extends JFrame{// JFrame 对应窗口 可以理解为一个画框
//定义一个面板
private MyPhoto mp=null;
public static void main(String[] args) {
new Demo3();
}
public Demo3(){//构造器
//初始化面板
mp=new MyPhoto();
//把面板放到窗口
this.add(mp);
//设置窗口大小
this.setSize(400,300);
this.setVisible(true);//可以显示
this.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);//当点击窗口的X,程序完全退出
}
}
//先定义一个MyPhoto(相当于画笔),继承JPanel
class MyPhoto extends JPanel {
@Override
public void paint(Graphics g) {//绘图方法 //paint(Graphics g) 绘制组件
// Graphics(提供很多绘图方法) g(画笔)
super.paint(g);//调用父类完成初始化
//画一个圆形
//System.out.println("paint被执行");
//当程序第一次运行时,窗口最大化和最小化,repaint()刷新组件外观 程序会自动调用paint()方法来绘制组件
//画椭圆边框
//g.drawOval(10,10,100,100);//前俩参数椭圆的左上角坐标 第三个参数宽度 第四个参数高度
//画直线
//g.drawLine(10,10,200,200);//前俩参数起点 后俩参数终点
//画矩形边框
//g.drawRect(10,10,50,50);//前俩参数矩形的左上角坐标 第三个参数宽度 第四个参数高度
//填充矩形
//g.setColor(Color.BLACK);//先设置画笔颜色
//g.fillRect(10,10,50,50);//前俩参数矩形的左上角坐标 第三个参数宽度 第四个参数高度
//填充椭圆
//g.setColor(Color.BLACK);//先设置画笔颜色
//g.fillOval(10,10,50,50);//前俩参数椭圆的左上角坐标 第三个参数宽度 第四个参数高度
//画字符串
g.setColor(Color.BLACK);//设置颜色
g.setFont(new Font("微软雅黑",Font.BOLD,40));//设置字体
g.drawString("主线任务:夺回秋雅",0,50);//这里设置的坐标是左下角
}
}*/
//java事件处理机制 委派事件模型 当事件(键盘事件,鼠标事件,窗口事件)发生,产生事件对象,会把信息传递给事件监听者来处理
/*
public class Demo3 extends JFrame {
MyPanel mp=null;
public static void main(String[] args) {
new Demo3();
}
public Demo3(){
mp=new MyPanel();
this.add(mp);
this.setSize(400,300);
this.addKeyListener(mp);//窗口JFrame对象可以对键盘进行监听
this.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
this.setVisible(true);
}
}
//画板 画出小球
//(MyPanel)事件监听者是一个类 它实现了KeyListener接口 他就可以作为一个事件监听者 对接收到的信息进行处理
class MyPanel extends JPanel implements KeyListener {//KeyListener 监听器 可以监听键盘事件
//为了让小球移动,把他左下角的坐标设为变量
int x=10;
int y=10;
@Override
public void paint(Graphics g) {
super.paint(g);
g.fillOval(x,y,20,20);//默认黑色
}
@Override
public void keyTyped(KeyEvent e) {
//有字符输出就会触发
}
@Override
public void keyPressed(KeyEvent e) {
//当某个键按下就会触发
//System.out.println((char)e.getKeyCode()+"被按下");
//根据用户按下不同键来处理小球的移动(上下左右的键)
if(e.getKeyCode()==KeyEvent.VK_DOWN){//KeyEvent.VK_DOWN就是向下移动的箭头对应的code 在java中每一个键,会分配一个int
y++;
}else if(e.getKeyCode()==KeyEvent.VK_UP){
y--;
}else if(e.getKeyCode()==KeyEvent.VK_LEFT){
x--;
}else if(e.getKeyCode()==KeyEvent.VK_RIGHT){
x++;
}
//让面版重绘
this.repaint();//repaint()刷新组件外观 程序会自动调用paint()方法来绘制组件
}
@Override
public void keyReleased(KeyEvent e) {
//当某个键松下就会触发
}
}
*/
/*
进程是指运行中的程序
比如我们使用QQ,就启动了一个进程,系统就会为该进程分配空间 进程是程序的一次执行程序,或是正在运行中的程序
线程是由进程创建的一个实例化对象,一个进程有多个线程,就好比一个QQ打开多个聊天页面
单线程:同一时刻,只允许有一个线程 多线程:同一时刻,可以有多个线程
并发:同一时刻,多个任务交替执行 单核cpu实现多任务就是并发 人开车打电话
并行:同一时刻 ,多个任务同时执行,多核cpu可以实现并行
*/
/*public class Demo3 {
public static void main(String[] args) {
Runtime runtime=Runtime.getRuntime();
//获取当前电脑cpu数量
int cpu=runtime.availableProcessors();
System.out.println("当前cpu个数"+cpu);
}
}*/
//创建线程的两种方式 1.继承Thread类,重写run方法 2.实现Runnable接口 重写run方法
/*public class Demo3 {
public static void main(String[] args)throws InterruptedException {
Dog dog=new Dog();
dog.start();//启动线程 ;
// start()本质是调用start0() ,该线程不一定立马被执行,只是将线程变成了可运行状态,具体什么时候执行,取决于CPU
// start0是本地方法 ,JVM调用,底层是c或c++
//真正实现多线程效果是start0,而不是重写的run
//当main线程启动一个子线程 Thread-0 主线程不会阻塞,会继续执行
for(int i=0;i<100;i++){
System.out.println("主线程i="+i);
Thread.sleep(100);//让主线程休眠
}
}
}
class Dog extends Thread{
int count=0;
@Override
public void run() {//重写run方法 写上自己的业务逻辑
while(true){
super.run();
System.out.println("汪汪汪,我是招财"+(++count)+Thread.currentThread().getName());
try {
Thread.sleep(1000);//让该线程休眠一秒
} catch (Exception e) {
System.out.println(e.getMessage());
}
if(count==100){
break;//当count到10 退出while 这是线程也就退出~
}
}
}
}*/
//java是单继承的,在某些情况下一个类可能继承了某个父类 这时用Thread类方法来创建线程显然不可能
//但我们可以实现Runnable接口来创建线程
/*public class Demo3 {
public static void main(String[] args) throws InterruptedException {
Dog dog=new Dog();
//dog.start(); 这里不能调用start
Thread thread=new Thread(dog);
//创建了Thread对象,把dog对象(实现Runnable),放入Thread 这里底层使用了代理模式(设计模式)
thread.start();
//如果通过main线程去控制dog线程的终止 必须修改loop --->通知方式
Thread.sleep(1000);//让主线程休眠5s,再通知dog线程退出
dog.setLoop(false);
}
}
class Dog implements Runnable{
private int count=0;
//设置一个控制变量
private boolean loop=true;
//线程终止 1.当线程完成任务会自动退出 2.还可以通过变量来控制run方法 即通知方式
public void setLoop(boolean loop) {
this.loop = loop;
}
@Override
public void run() {
while(loop){
try {
Thread.sleep(50);
} catch (InterruptedException e) {
System.out.println(e.getMessage());
}
*//*if(count==10){
break;
}*//*
System.out.println("汪汪汪,我是招财又进宝"+(++count));
}
}
}*/
/*public class Demo3 {
public static void main(String[] args) {
Dog dog=new Dog();
MoFang mofang=new MoFang(dog);
mofang.start();
}
}
class Animal{
}
class Dog extends Animal implements Runnable{
@Override
public void run() {
System.out.println("汪汪汪,招财有进宝");
}
}
class MoFang implements Runnable{
private Runnable target=null;
@Override
public void run() {
if(target!=null){
target.run();
}
}
public MoFang(Runnable target) {
this.target = target;
}
public void start(){
start0();
}
public void start0(){
run();
}
}*/
//通过继承Thread 和实现Runnable接口来创建线程本质没有区别 实现Runnable接口更加适合多个线程共享一个资源的情况,并且避免了单继承的限制
/*public class Demo3 {
public static void main(String[] args) throws InterruptedException {
Test test=new Test();
//用户线程也叫工作线程,当线程的任务执行完或通知方式结束
//守护线程 一般为工作线程服务的,当用户线程执行完,守护线程自动结束
//如果我们希望当main线程结束后,子线程自动结束 只需要将子线程设为守护线程即可
// Test test = new Test();
// test.setDaemon(true);
// test.start();
线程的常用方法 1. 线程的礼让,让出cpu,但里让时间不确定,所以不一定礼让成功 Thread.yield();
2.线程的插队,插队线程一旦成功,则肯定先执行完插入线程的所有任务 test.join();
//测试相关方法
test.setName("招财");//设置线程名字
test.setPriority(Thread.MIN_PRIORITY);//更改线程优先级 1最小的 主线程休眠后执行
test.start();
//start底层会创建新的线程,调用run(run就是一个普通方法调用,不会启动新的线程)
//主线程打印5个hello 然后中断 子线程的休眠
for(int i=0;i<5;i++){
Thread.sleep(1000);
System.out.println("hello"+i);
}
//getPriority() 获取线程优先级
System.out.println(test.getName()+"线程优先级"+test.getPriority());//getName返回该线程名字
test.interrupt();//中断线程 ,但并没有真正的结束线程 所以一般用于中断正在休眠的线程
}
}
class Test extends Thread{
@Override
public void run() {
while(true){
for(int i=0;i<100;i++){
System.out.println(Thread.currentThread().getName()+"吃饭饭"+i);
}
try {
Thread.sleep(20000);//休息20s
} catch (InterruptedException e) {
//当线程执行到一个interrupt方法时,就会catch一个异常,可以加入自己的代码
System.out.println(Thread.currentThread().getName()+"被打断了");
}
}
}
}*/
/*线程同步 Synchronized 局限性:导致程序执行效率低
同步代码块 synchronized(对象){//需要被同步的代码}
synchronized 放在方法声明中-同步方法 public synchronized void test(){//需要被同步的代码}
同步方法(非静态)的锁可以是this,也可以是其他对象(要求同一个对象)
同步方法(静态)的锁为当前类本身 public synchronized static void test()锁是加在 XXX.class
互斥锁:任何时候只有一个线程访问该对象
多个线程占用对方锁资源,但不肯想让,导致死锁 我:先玩会手机再写作业 父母:先写完作业在玩手机
释放锁:执行结束;遇到break或return;因为异常结束;同步代码块,同步方法中执行了线程对象wait()方法,线程暂停,释放锁
不会释放锁的情况 : 1.程序调用了Thread.sleep 和Thread.yield 2.调用了该线程的suspend()方法将线程挂起(尽量避免使用suspend()和resume()已过时)
*/
/* public class Demo3 {
public static void main(String[] args) {
Money money1=new Money();
Thread thread1=new Thread(money1);
thread1.setName("thread1");
Thread thread2=new Thread(money1);
thread2.setName("thread2");
thread1.start();
thread2.start();
}
}
class Money implements Runnable{
private int money=10000;
@Override
public void run() {
while(true){
//判断余额是否足够
synchronized(this) {
if (money < 1000) {
System.out.println("余额不足");
break;
}
money -= 1000;
System.out.println(Thread.currentThread().getName() + "取出1000当前余额还有" + money);
}
try {
Thread.sleep(1000);//休眠一秒 不然太快看不出效果
} catch (InterruptedException e) {
e.printStackTrace();
}
}
}
}*/
/*
文件就是保留数据的地方 word txt excel都是文件
文件在程序中以流的方式来操作 java程序--(输出流)--->文件----(输入流)---->java程序
*/
/*public class Demo3 {
public static void main(String[] args) {
}*/
//1.根据路径创建File对象
/*@Test
public void File1(){
String route="d:\\new1.txt";
File file=new File(route);
//文件相应的方法
System.out.println("文件名字="+file.getName());
System.out.println("文件绝对路径="+file.getAbsolutePath());
System.out.println("文件父级目录"+file.getParent());
System.out.println("文件大小(字节)"+file.length());
System.out.println("文件是否存在"+file.exists());//F
System.out.println("是不是一个文件"+file.isFile());//F
System.out.println("是不是一个目录"+file.isDirectory());// F目录=文件夹
try {
file.createNewFile();
System.out.println("文件创建成功");
} catch (IOException e) {
e.printStackTrace();
}
}*/
//2. 根据父目录文件+子路径构建
/*@Test
public void File2(){
File father=new File("d:\\");
String name="new2.txt";
File file=new File(father,name);
//这里的file在Java中只是一个对象
try {
file.createNewFile();
//只有createNewFile 才是真正的在磁盘创建文件
System.out.println("创建成功");
} catch (IOException e) {
e.printStackTrace();
}
}*/
//3. 根据父目录+子路径创建
/* @Test
public void File3(){
//String route="d:\\";
String route1="d:/";//也可以这样写
String name="new3.txt";
//File file=new File(route,name);
File file=new File(route1,name);
try {
file.createNewFile();
System.out.println("创建成功");
} catch (IOException e) {
e.printStackTrace();
}
}*/
/*@Test
//mkdir创建一级目录 mkdirs创建多级目录
public void test(){
String route = "D:\\demo\\a\\b";
File file=new File(route);
if(file.exists()){
System.out.println(route+"该文件存在");
}else{
if(file.mkdirs()){
System.out.println(route+"创建成功");
}else{
System.out.println(route+"创建失败");
}
}
//file.delete();//delete删除文件
}*/
//}
/*
IO流 Input(磁盘光盘数据到程序(内存)中)/Output(将内存的数据输出到磁盘光盘)的缩写 用于读写文件,网络通讯等
java程序中,对于数据的输入/输出操作通过流(stream)的方式进行
按操作数据单位不同分为 字节流(常用于二进制文件) 字符流(文本文件)
字节流 输入流 InputStream 输出流OutputStream 字符流 输入流 Reader 输出流 Writer 这四个都是抽象类
有这四个类派生出的子类名称都以父类名作为子类后缀名
InputStream(字节输入流)抽象类是所有类字节输入流的超类 FileInputStream文件输入流 BufferedInputStream缓冲字节输入流 ObjectInputStream对象字节输入流
*/
//public class Demo3 {
/*@Test
public void readFile1(){
String route="d:\\hello.txt";
int readNum=0;
FileInputStream fileInputStream = null;
byte[] array=new byte[8];//字节数组 一次读取8个字节
try {
fileInputStream=new FileInputStream(route);//创建FileInputStream对象用于读取文件
//readNum=fileInputStream.read();//从该输入流读取一个字节,如果没有输入可用,此方法阻止 返回-1则读取完毕
//System.out.println((char)readNum);
//while((readNum=fileInputStream.read())!=-1){
// System.out.print((char)readNum);
//}
while((readNum=fileInputStream.read(array))!=-1){
System.out.print(new String(array,0,readNum));
}
} catch (IOException e) {
e.printStackTrace();
}finally{
//关闭文件 释放资源
try {
fileInputStream.close();
} catch (IOException e) {
e.printStackTrace();
}
}
}*/
/*@Test
public void writeFile1(){
String route="d:\\test.txt";
FileOutputStream fileOutputStream=null;
try {
//fileOutputStream=new FileOutputStream(route);
fileOutputStream=new FileOutputStream(route,true);//追加
//写入一个字节
//fileOutputStream.write('A');
//写入字符串
String str="hello,world";
//getBytes()可以把字符串转换为字节数组
//fileOutputStream.write(str.getBytes());
fileOutputStream.write(str.getBytes(),0,5);
} catch (IOException e) {
e.printStackTrace();
}finally {
try {
fileOutputStream.close();
} catch (IOException e) {
e.printStackTrace();
}
}
}*/
//文件拷贝
/* @Test
public void FileCopy(){
String route1="d:\\qq.png";
String route2="d:\\qq1.png";
FileInputStream fileInputStream=null;//创建文件输入流 将文件读入到程序
FileOutputStream fileOutputStream=null;//创建文件输出流 将文件写入到指定文件
try {
fileInputStream =new FileInputStream(route1);
fileOutputStream=new FileOutputStream(route2);
//定义一个数组 提高读取效率
byte[] array=new byte[1024];
int readNum=0;
while((readNum=fileInputStream.read(array))!=-1){
//一边读 一边写
fileOutputStream.write(array);
}
System.out.println("拷贝ok");
} catch (IOException e) {
e.printStackTrace();
}finally{
//关闭输入流和输出流 释放资源
try {
if(fileInputStream!=null){
fileInputStream.close();
}
if(fileOutputStream!=null){
fileOutputStream.close();
}
} catch (IOException e) {
e.printStackTrace();
}
}
}*/
/*
FileReader和FileWriter是字符流
FileReader: new FileReader(File/String) read每次读取单个字符,返回该字符,如果到文件末尾返回-1
read(char[])批量读取多个字符,返回读取的字符数,文件末尾返回-1
new String(char[])将char[]转换成String
new String(char[],off,len) 将char[]指定部分转换成String
FileWriter: new FileWriter(File/String) 覆盖模式,相当于流的指针在首段 new FileWriter(File/String,true) 追加模式,相当于指针在尾端
write(int) 写个单个字符 write(char[]) 写入指定数组 write(char[],off,len)写入数组指定部分 write(string)写入字符串
write(string,off,len)写入字符串的指定部分 toCharArray:将字符串转换成char[]
FileWrite使用后,必须要关闭close或刷新flush,否则写入不到指定文件 fileWrite.close等价于fileWrite.flush()+关闭
数据源就是存放数据的地方
节点流可以从一个特定的数据源读写文件 FileReader FileWriter 底层流/低级流 直接与数据源相连
处理流(也叫包装流)是在节点流或处理流智商,为程序提供更大的读写功能 BufferedReader(有属性Reader) BufferedWriter(有属性Writer)
处理流不会直接和数据源相连 使用了修饰器设计模式 优点:性能的提高(主要通过缓冲的方式提高输入输出的效率) 操作便捷
处理流 BufferedReader BufferedWriter 按照字符来读取数据 关闭时,只需关闭外层流即可 不要去操作二进制文件(声音 视频 docx等)
*/
/*@Test
public void ChuLiLiu1() throws IOException {
String route="d:\\a.txt";
BufferedReader bufferedReader=new BufferedReader(new FileReader(route));
String Line;//按行读取 效率高
while((Line=bufferedReader.readLine())!=null){//bufferedReader.readLine()按行读取文件 当返回null 表示文件读取完毕
System.out.println(Line);
}
bufferedReader.close();//关闭流
}*/
/*@Test
public void ChuLiLiu2() throws IOException {
String route="d:\\b.txt";
BufferedWriter bufferedWriter=new BufferedWriter(new FileWriter(route));
bufferedWriter.write("hello,java1");
bufferedWriter.newLine();//差一个和系统相关的换行
bufferedWriter.write("hello,java2");
bufferedWriter.newLine();
bufferedWriter.write("hello,java3");
bufferedWriter.newLine();
bufferedWriter.close();
}*/
/*@Test
public void ChuLiLiuCopy() throws IOException {
String start="d:\\a.txt";
String end="d:\\b.txt";
BufferedReader read=new BufferedReader(new FileReader(start));
BufferedWriter write=new BufferedWriter(new FileWriter(end));
String line;
while((line= read.readLine())!=null){
write.write(line);//每读一行就写入
write.newLine();
}
//关闭流
if(read!=null){
read.close();
}
if(write!=null){
write.close();
}
}*/
/* BufferedInputStream BufferedOutputStream字节流
对象流 ObjectInputStream(提供反序列化功能) ObjectOutputStream(提供序列化功能) 序列化就是保存数据时,保存数据的值和数据类型 反序列化就是恢复数据的值和数据类型
一个类是可序列化必须实现两个接口之一 Serializable//这是一个标记接口,没有方法 Externalizable该接口有方法需要实现,因此我们一般实现上面的
序列化具有可继承性 某类实现类序列化 其子类也已经默认实现了序列化
序列化对象,默认将所有的成员都序列化 但static 或 transient修饰时的成员不会
*/
/*@Test
public void ObjectOutStream_() throws IOException, ClassNotFoundException {
String route="d:\\test.txt";//序列化后 保存文件格式不是存文本 而是按它的格式来保存
ObjectOutputStream objectOutStream=new ObjectOutputStream(new FileOutputStream(route));
//序列化数据
objectOutStream.writeInt(100);// int-->Integer(实现了Serializable)
objectOutStream.writeBoolean(true);
objectOutStream.writeChar('a');
objectOutStream.writeUTF("哈哈");
objectOutStream.writeObject(new Dog("旺财"));
objectOutStream.close();
System.out.println("数据保存完毕");
ObjectInputStream objectInputStream=new ObjectInputStream(new FileInputStream(route));//反序列化文件
//读取(反序列化)的顺序要和你保存的数据(序列化)顺序一致
System.out.println(objectInputStream.readInt());
System.out.println(objectInputStream.readBoolean());
System.out.println(objectInputStream.readChar());
System.out.println(objectInputStream.readUTF());
//如果我们需要调用Dog方法,需要向下转型
Object dog=objectInputStream.readObject();
System.out.println("运行类型="+dog.getClass());//底层 Object->Dog
System.out.println(dog);
Dog dog1=(Dog) dog;
System.out.println(dog1.getName());
objectInputStream.close();
}*/
// public static void main(String[] args) throws IOException {
/*
标准输入输出流 类型 默认设备 编译类型 运行类型
System.in标准输入 InputStream 键盘 InputStream BufferedInputStream
System.out标准输出 PrintStream 显示器 PrintStream PrintStream
*/
//System.out.println(System.in.getClass());
//System.out.println(System.out.getClass());
/*转换流 InputStreamReader(可以传入一个InputStream对象,并且可以指定处理编码) OutputStreamWriter
当处理纯文本数据时 使用字符流效率更高 并且可以解决中文问题 所以建议将字节流转为字符流
*/
/*String route="d:\\test.txt";
InputStreamReader inputStreamReader=new InputStreamReader(new FileInputStream(route),"gbk");
//InputStreamReader:Reader的子类 可以将InputStream(字节流)包装成Reader(字符流)
BufferedReader bufferedReader=new BufferedReader(inputStreamReader);
String str=bufferedReader.readLine();
System.out.println("读取的内容"+str);
bufferedReader.close();
String route1="d:\\test1.txt";
String format="gbk";
OutputStreamWriter outputStreamWriter=new OutputStreamWriter(new FileOutputStream(route1),format);
//OutputStreamWriter: Writer的子类,可以将OutputStream(字节流)包装成Writer(字符流)
outputStreamWriter.write("hello,world");
System.out.println("保存成功");
outputStreamWriter.close();*/
//打印流 PrintStream 和 PrintWriter 打印流只有输出流,没有输入流
/*PrintStream out=System.out;
out.print("hahahha");//在默认情况下 PrintStream输出数据的位置是 标准输出 即显示器
//因为print底层调用的write 我们也可以直接调用write进行打印输出
out.write("nihao".getBytes());
out.close();
//我们可以去修改打印流的输出位置
System.setOut(new PrintStream("d:\\test.txt"));
System.out.println("hello,world");
//PrintWriter printWriter=new PrintWriter(System.out);
PrintWriter printWriter=new PrintWriter(new FileWriter("d:\\test1.txt"));
printWriter.print("hi,hahha");
printWriter.close();*/
/*Properties(父类是Hashtable) 专门用于读写配置文件的集合类 (键--值)
.load() 加载配置文件的键值到properties对象
getProperty(key) 根据键获取值
setProperty(key,value) 设置键值到properties对象 有key修改没key创建
store 将properties中的键值存储到配置文件,在idea中 如果还有中文,会存储为unicode码
list 将数据显示指定位置
*/
/* }
}*/
/*
class Dog implements Serializable{
private String name;
private static final long serialVersionUID=1L;//serialVersionUID 序列化的版本编号,可以提高兼容性
public String getName() {
return name;
}
public Dog(String name) {
this.name = name;
}
@Override
public String toString() {
return "Dog{" +
"name='" + name + '\'' +
'}';
}
}
*/