一、类的对象的创建和使用
package com.XiJian.java;
public class Duixiang {
public static void main(String[] args) {
Car c1 = new Car();
c1.info();
// c1.setName("玛莎拉蒂");
// c1.setWheel(4);
c1.name = "劳斯莱斯";
c1.wheel = 4;
c1.info();
Factory f1 = new Factory();
Car c2 = f1.produceCar();
f1.describeCar(c2);
Car c3 = f1.produceCar("奥迪",4);
f1.describeCar(c3);
}
}
class Factory
{
//方法的重载
public Car produceCar()
{
return new Car();
}
public Car produceCar(String n,int w)
{
Car c = new Car();
c.name = n;
c.wheel = w;
return c;
}
public void describeCar(Car c)
{
c.info();
}
}
class Car
{
//1.属性
String name;
int wheel;
//2.方法
public void info()
{
//show
System.out.println("name:"+ name +" wheel:"+ wheel);
}
public void show()
{
System.out.println("我是第一辆车");
}
public String getName()
{
return name;
}
// public void setName(String n)
// {
// name = n;
// }
// public void setWheel(int w)
// {
// wheel = w;
// }
}
二、对象作为参数的传递练习
package com.xijian.java;
/*
* 实验
1、将对象作为参数传递给方法。
题目要求:
(1)定义一个Circle类,包含一个double型的radius属性代表圆的半径,一个findArea()方法返回圆的面积。
(2)定义一个类PassObject,在类中定义一个方法printAreas(),该方法的定义如下:
public void printAreas(Cirlce c, int time)
在printAreas方法中打印输出1到time之间的每个整数半径值,以及对应的面积。例如,times为5,则输出半径1,2,3,4,5,以及对应的圆面积。
在main方法中调用printAreas()方法,调用完毕后输出当前半径值。
*/
class Shiyan {
}
class Circle
{
double radius;//半径
public double findArea()
{
return radius*radius*Math.PI;
}
public void setRadius(double r)
{
radius = r;
}
public double getRadius()
{
return radius;
}
}
public class PassObject
{
public void printAreas(Circle c,int time)
{
System.out.println("Radius" + "\t\t" + "Area");
for(int i = 1 ;i<= time;i++)
{
c.setRadius(i);
System.out.println(c.getRadius() + "\t\t" + c.findArea());
}
c.setRadius(time+1);
}
public static void main(String[] args)
{
PassObject p = new PassObject();
Circle c = new Circle();
p.printAreas(c, 5);
System.out.println("now radius is "+c.getRadius());
}
}
三、匿名类对象的使用
/*
* 匿名对象是没有名字的一个对象,实际上是值开辟了堆内存空间,而没有栈内存指向的对象。
* 匿名对象的特点:1.匿名对象是没有被其他对象所引用,即没有栈内存指向。
* 2.由于匿名对象没有栈内存指向,所以其只能使用一次,之后就变成无法找寻的垃圾对象,故此会被垃圾回收器收回。
*/
package com.xijian.java;
public class NoNameObject {
public void say() {
System.out.println("面朝大海,春暖花开");
}
public static void main(String[] args) {
//这是匿名对象,没有被其他对象所引用
new NoNameObject().say();//相当于 NoNameObject n = new NoNameObject(); n.say();
}
}
四、对象的比较
package com.xijian.java;
public class ComepareObject2 {
public static void main(String[] args) {
String str1 = new String("java");
String str2 = new String("java");
String str3 = str2;
if(str1.equals(str2)) {
System.out.println("str1 equals str2");
}
else {
System.out.println("str1 not equals str2");
}
if(str2.equals(str3)) {
System.out.println("str2 equals str3");
}
else {
System.out.println("str2 not equals str3");
}
}
}
//由此可见对象的equals方法是比较两个对象的内容的
五、类的构造方法
/*
* 构造方法:类名称 对象名称 = new 类名称();
* class类名称{
* 访问权限 类名称(类型1 参数1,类型2 参数2,……)//构造方法
* {
* 程序语句
* //没有返回值
* }
* }
* 注意:1.构造方法名称和其所属的类名必须一致
* 2.构造方法没有返回值,也不可以使用void
* 3.构造方法也可以像普通方法一样被重载
* 4.构造方法不能被static和final修饰
* 5.构造方法不能被继承,子类如需要使用父类的构造方法需要使用super关键字
* 6.构造方法在对象产生时自动执行一次,用来对象成员属性的初始化
*
*/
package com.xijian.java;
public class TestConstruct {
public static void main(String[] args) {
Person p = new Person(12);
p.show("以上是构造方法的演示");
}
}
class Person{
public Person(int x) {
a = x;//用构造方法的x来初始化私有变量a
System.out.println("构造方法被调用");
System.out.println("a = "+a);
}
public void show(String msg) {
System.out.println(msg);
}
private int a;
}
六、构造方法的重载
package com.xijian.java;
public class ConstructOverload {
public static void main(String[] args) {
Person p1 = new Person(18);//调用构造函数
Person p2 = new Person(18,"席剑");//调用构造函数
p1.show();
p2.show();
}
}
class Person{
private String name;
private int age;
//含有一个整形参数的构造方法
public Person(int age) {
name = "kehr";//随便用一个值去初始化name
this.age = age;
}
//含有一个字符串型的参数和一个整形参数的构造方法
public Person(int age,String name) {
this.name = name;
this.age = age;
}//构造方法的重载
public void show() {
System.out.println("我叫:"+name+" 我今年:"+age+"岁");
}
}
ps:当有构造函数并且构造函数的形参表列有参数的时候,在创建一个对象的时候如果无参数进行创建对象会报错,提示一个类无法解析其类型
七、构造方法的私有化
/*
* 构造方法的私有化:访问权限分为public、private、默认访问。
* 当构造方法之前的修饰符为public的时候,它课在程序的任何地方被调用,所以新创建的对象也都可以自动调用它。
* 如果构造方法被设为private,那么其他类中就无法调用该构造方法。换句话说,在本类之外,就不能通过new关键字调用该构造方法创建该类的实例化对象
*/
package com.xijian.java;
class PrivateDemo {
//构造方法被私有化
private PrivateDemo() {}//一个私有的构造方法
public void print() {
System.out.println("Hello Java!");
}
}
//实例化 PrivateDemo对象
public class PrivateCallDemo{
public static void main(String[] args) {
PrivateDemo demo = null;
demo = new PrivateDemo();//出错 因为构造方法在外类中不可见
demo.print();
}
}
报错信息:Exception in thread "main" java.lang.Error: 无法解析的编译问题:
构造函数 PrivateDemo()不可视
at com.xijian.java.PrivateCallDemo.main
(1)正确的构造方法私有化使用应该如下
public class PrivateConstructor{
private PrivateConstructor() {
System.out.println("构造方法已被私有化!");
}
public static void main(String[] args) {
new PrivateConstructor();//在本类中调用构造方法,并且创建了一个匿名对象
}
}
(2)利用私有构造方法的实例
package com.xijian.java;
public class TestSingleDemo {
public static void main(String[] args) {
//声明一个Person类的对象
Person p;//只在栈空间中分配了内存空间,p所指的对象并不存在
//虽私有化Person类的构造方法,但可以通过Person类公有接口获得Person实例化对象
p = Person.getPERSON();
System.out.println("姓名:"+p.name);
}
}
class Person{
String name;
//在本类声明Person对象PERSON,注意此对象用final表姐,表示该对象不可更改
private static final Person PERSON = new Person();
private Person(){
name = "席剑";
}//私有化构造方法,外部类无法通过其创建对象
public static Person getPERSON() {
return PERSON;
}
}
八、递归
/*
* 函数直接调用自身或者间接调用自身,叫做递归,在编写代码时一定要注意要有终止条件,终止条件课用if语句来控制。
* 计算1+2+3+……+n
*/
package com.xijian.java;
public class RrecursionMethod {
public int addNonrecursion(int n) {
//非递归方法实现
int result = 0;
for(int i = 0;i<=n;i++) {
result += i;
}
return result;
}
//递归方法实现
public int addRecuesion(int n) {
//递归出口,当n小于1时函数会逐层返回
if(n<=1) return n;
return n+addRecuesion(n-1);
}
public static void main(String[] args) {
RrecursionMethod r = new RrecursionMethod();
int result = r.addNonrecursion(20);
System.out.println(result);
int result1 = r.addRecuesion(20);
System.out.println(result1);
}
}
累了累了 今天学的东西敲的代码有点多 休息休息……
九、方法的值传递机制
1、形参如果是基本数据类型,将实参的值传递给基本数据类型的形参变量(同样存放在栈空间的变量)。
2、形参如果是引用数据类型,将实参的值(实际上是对应堆空间的实际对象的地址)传递给引用数据类型的形参变量。
比如一个交换方法swap,如果想交换main方法里的i,j的值,就必须把swap交换方法直接写在main方法里,不然交换的只是swap形参变量的值,对于原变量并不改变。当然还可以将 i,j声明在一个类里,去创建一个对象,将swap方法的形参改为对象,这样就变成了传址,则能改变对应i,j的值
十、可变个数的形参的方法
/*
* 可变个数的形参的方法
* 1.格式:对于方法的形参: 数据类型 ... 形参名
* 2.可变个数的形参的方法与同名的方法之间构成重载
* 3.可变个数的形参在调用时,个数从0开始,到无穷多个都可以
* 4.使用可变个数的形参的方法与方法的形参使用数组是一致的,(自我暂时认为就是通过一种数组存储)
* 5.在方法中如果出现可变个数的形参,一定要放在形参列表的最后
* 6.在一个方法中,最多声明一个可变个数的形参。
*/
package com.xijian.java;
public class Demo {
public static void main(String[] args) {
Demo d = new Demo();
String str1 = "China";
d.hello1();//在没有参数的情况下还是默认无参数的重载方法
d.hello1(str1);//只有传str1这个变量才会执行第二个重载方法,如果传一个字符串便会认为是执行第三个重载方法
d.hello1(new String[] {"Japan","American"});
}
public void hello1() {
System.out.println("hello world");
}
public void hello1(String str1) {
System.out.println("hello "+str1);
}
public void hello1(String ... args) {
for(int i = 0;i<args.length;i++) {
System.out.println("hello"+"$"+args[i]);
}
}
}