【转载】Java程序设计入门 (一)

阅读本文之前请先学习博客中的另一文章《面向对象起步 --- 封装、继承、多态》, 以建立面向对象编程的基本概念. 本文将不再复述其中已提到的概念和术语.

关于Java相对于其它程序设计语言的优点本文不再赘述, 事实上, 就设计语言而言并无优劣之分, 关键看其是否能满足项目需要.
同样, 本文也不对如何搭建开发环境, 使用什么样的开发工具进行阐述, 网上有很多此类文章, 请自行查阅…… 

在开始学习之前, 请确保你的计算机上安装了如下软件:
(1) JDK : Java开发工具包, 官方下载地址: http://www.oracle.com/technetwork/java/javase/downloads/index.html . 或者, 打开度娘, 搜索JDK安装包, 下载一个较新版本的, 安装即可. 目前最新版本是JDK 7, 当然使用JDK 6也是可以的, 并不影响本文的学习.
(2) Eclipse : 集成开发环境 (IDE), 官方下载地址 http://www.eclipse.org/downloads, 下载 Standard / For JavaEE Developer/ For Java Developer版本均可, 但应根据你的操作系统选择32位版或64位版. 下载到的文件解压后无须安装, 运行eclipse.exe即可启动Eclipse开发环境.

~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
本节关键词: 类、对象、属性、方法、重载、可访问性控制、构造函数, 代词this
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~

好吧, 这就开始吧……

1. 类、对象

在Java的世界里, 一切都是从创建类开始, 程序是无法独立存在于类之外的. 类和对象是面向对象理论里实现封装的重要手段.
OK, 启动Eclipse, 我们来创建一个类……
首次启动Eclipse的过程中会出现一个要求指定工作空间(workspace)的对话框, 指定一个路径. 今后你的项目文件将被存储在该路径下,所以请记住它. 
之后, 在Eclipse主界面左侧的Package Explorer视图中空白处点右键 → New → Java Project 新建一个Java项目, 如下图. (首次启动Eclipse可能会显示Welcome视图, 关闭它就可以看到Package Explorer视图)

Java程序设计入门 (一) - bailey - Baileys Blog
 

在之后出现的 "New Java Project" 对话框的 "Project Name" 输入框中填入项目名称 (随意), 此处我们填入 "JavaStudy", 直接点击 Finish 按键即可. 
此时, Package Explorer 中即出现新建的项目. 逐层展开项目可看到Eclipse已经帮我们创建了一个名为src的源文件夹, 并引入了一些常用的 jar 文件(这些文件被归入到了JRE System Library中), 如下图:

Java程序设计入门 (一) - bailey - Baileys Blog
 
src 源文件夹是用来存放我们写的程序.
默认引入的这些 jar 文件其实是别人已经写好了的一些程序, 经过打包之后形成一个个独立的 jar 文件. 这些 jar 是一般Java项目所需的, 暂时无须知道他们的用途…… 今后可能我们会使用到更多的第三方库 ( jar ), 也需要同样引入 ( 如何做? 暂时别管 ).

OK, 接着来…… 
现在我们要在JavaStudy项目中新建我们的第一个类……
在src图标上点击右键 → New → Class, 出现如下图所示的 "New Java Class" 对话框.

Java程序设计入门 (一) - bailey - Baileys Blog
 
在 Package 处输入Package 的名称 ( 本文输入com.bailey.study.animal )
在 Name 处输入类的名称 ( 本文输入Pig )
点击 "Finish"…… 这样就创建了一个名为 Pig 的类 ( 猪类, 呵呵~).

疑问很多吧, 呵呵, 解释一下……

package : 通常称为"". 为了避免类名冲突 (不同的类名称相同), 通常需要为类指定它所在的包. 在其它的程序设计语言里也有类似的东西, 可能会被称为"命名空间(namespace)". 习惯上包名一般以"公司域名倒序.项目名"开头. 在本例中, 指定了包名为 com.bailey.study.animal, 类名为Pig之后, 该类的完整名称其实是 com.bailey.study.animal.Pig, 这样就可以避免重名了……


习惯上, 包名以小写字母开头, 以"."分隔各个部分. 类名则以大驼峰法(Camel-Case)命名, 即大写字母开头, 组成名称的各单词首字母大写, 其余字母小写. (参阅百度百科-骆驼命名法)

OK, 我们来看看Eclipse生成了些什么吧……

Java程序设计入门 (一) - bailey - Baileys Blog 
  
可以看到, Package Explorer 中出现了新建的包和类, 而在右侧主视图中出现了 Pig.java 的源代码. ( 双击Package Explorer中的类名即可打开源码 )

相信你对那些花花绿绿的代码很好奇吧, 呵呵~ 简单解释一下(看注释)……
package com.bailey.study.animal;    // 指定类所在的包
/**
 * 定义"猪类". 
 * public是什么东东? 别管它, 等你长大了就知道了~
 */
public class Pig {
}
看到绿色的注释了吧, 注释风格是不是和C语言很像……

好……继续……, 我们为"猪类"添加2个属性: name, weight ( 名字, 体重 ) 和 一个方法: eat ( 吃 ) , 代码如下(注意看注释):
package com.bailey.study.animal;

public class Pig {

    public String name;         // 定义一个名为"name"的属性, 数据类型为 String (字符串)
    
    public String sex;		// 性别

    public void eat(String food) {     // 定义一个名为"eat"的方法, 接收一个 String 型的参数food, 无返回值 
       // 若属性 name 的值为 "小花", 参数 food 值为 "米饭", 则输出 "小花吃了米饭"
       System.out.println(name + "吃了" + food);
    }
}
嘿嘿, 就这么简单~   别傻看了, 快去试试吧……
注: 上面的代码并非推荐的写法, 更好的写法在本文最后, 所以…… 请坚持看完本文! 

好的, 到此为止我们定义了一个类 Pig, 那要怎么使用它呢? 
注意, Pig 只是一个类, 并非一头具体的猪, 它还吃不了东西, 就像我们不能说"猪类你去饭吧~", 这样谁知道你叫谁呢…… 应该说"小花吃饭去吧~", 也就是说, 我们得把猪类() 变成一头具体的猪(对象).
怎么变呢? 对了, 实例化! 代码大概是这样:  Pig p = new Pig();
但是, 这行代码写在那里呢? 总得有个调用方吧……  

OK, 现在就来创建另外一个类, 作为程序的入口, 并把"小花"生出来……

Come on! 一起来……

在 Package Explorer 视图中, src图标上点右键 → New → Package, 在弹出对话框中的Name处输入com.bailey.study.test, 创建一新的包. 

然后…… 在com.bailey.study.test包的图标上点击右键 → New → Class, 创建一个新的类命名为"HelloJava". 需要注意的是, 请选中 "New Java Class" 对话框中的 "public static void main(String[] args)" 复选框, 这样Eclipse会帮我们在新建的类中添加一个名称为 main 的方法, 这个方法将作为程序入口.

然后…… 打开HelloJava类的源代码 (已经自动打开了吧~), 在里面添加一些代码, 最终完成的样子如下:
  1: package com.bailey.study.test;

  2: import com.bailey.study.animal.Pig;   // 引入 Pig 类

  3: public class HelloJava {
  4: 
  5:     public static void main(String[] args) {
  6: 
  7:         Pig p = new Pig();     // 实例化, 将对象赋值给变量 p
  8: 	
  9:         p.name = "小花";       // 将对象 p 的name属性赋值为字符串"小花"
 10: 	
 11:         p.eat("米饭");         // 调用对象 p 的 eat 方法, 让它吃米饭
 12:    
 13:     }
 14: }
注意看一下上面的注释就能明白各行代码是什么意思了……
其中, 有一些不知道含意的关键词, 例如: public, static, 暂时别管他, 以后我们再解释……

对于上述代码中的第2行, 稍作解释……
当要使用的类与当前类不在同一个包(package)时就必须使用 import 关键词引入该类 (例如本例中的 Pig 类). 否则…… Java就不知道Pig从那来了吧! 把第2行删了试试? 呵呵~  这有点像其它程序设计语言中的 include/using……
为了省事, 可以使用Eclipse快捷键 Ctrl + Shift + O, 试试~


好了, 现在入口函数也有了, 怎么让程序运行起来呢?
在 Package Explorer 视图中找到 HelloJava 类点右键 → Run As → Java Application
看到了吗? 在 Eclipse 窗口的中的 Console 视图出现了 "小花吃了米饭", 呵呵, 这就运行起来了~ 如下图:

Java程序设计入门 (一) - bailey - Baileys Blog

Console 意为控制台, 这个视图中将显示程序的输出内容……

也可以在 HelloJava 类的图标上点右键 → Debug As → Java Application, 这样会以"调试"方式启动程序(前面的叫"运行方式"). 在调试方式下, 程序运行到我们设置的"断点"就会暂停, 此时可以观察当前各个变量的当前值, 以便对程序进行排错. 
如何设置"断点"?  在想要设置"断点"的代码前双击即可, 之后, 会在断点所在的行前面出现一个蓝色的圆点, 如下图:

Java程序设计入门 (一) - bailey - Baileys Blog
 
快以调试方式运行一次试试呀……
以后遇到程序报错就别老傻坐着看了, 设个断点调试一下吧!  


好了, 在继续往下看之前先暂停3分钟…… 整理一下思路, 想想我们都做了些什么? 它们之间的关系是如何的?
过程大概是这样: 创建类 → 实例化 → 调用对象的方法


2. 重载(Overload)

前面的例子中, 我们只为Pig类定义一种"吃法": eat(String food), 无论这食物是凉的或是烫的, 这猪都一口就吃下去了. 但事实上, 如果食物是比较烫, 恐怕得凉一会, 呵呵~  
于是, 我们想再多传一个参数给 eat 方法, 告诉它食物是否是烫的…… 程度该如何修改呢?
也许, 你想到的办法是修改原先的 eat 方法, 为它添加一个参数: isHot. 但其实没必要修改原先已有的那个 eat 方法, 只要为 Pig 类再增加一个同名的 eat 方法就好了.  ( 原先的 eat 方法可认为是一种默认吃法, 我们不想改它, 呵呵~)
如果你已经读完了《面向对象起步 --- 封装、继承、多态》, 那你应该明白, 这就是传说中的"重载"了, 如果还没有读…… 那建议先停一下, 去看看吧 (在那篇文章中提到的一些知识本文将不再重复)……
 
OK, 看代码……
  1: public void eat(String food) {
  2:   System.out.println(name + "吃了" + food);
  3: }
  4:     
  5: public void eat(String food, boolean isHot) {
  6:   if (isHot) {
  7:       System.out.println("等呀等... 终于凉了...");
  8:   }
  9: 
 10:   eat(food);       // 这里调用了第1行的那个eat方法
 11: } 
没什么好说的…… 关注一下第10行的注释, Maybe 你悟到了点什么……
是的, Java会根据传入的参数, 自动选择一个最合适的方法去调用…… 
说到这里, 去把 HelloJava.java 中的 p.eat("米饭"); 改为 p.eat("米饭", true); 试试吧……

关于重载的一些概念和原则, 还是请阅读一下本博客中的另一篇文章《面向对象起步 --- 封装、继承、多态》, 此处不再赘述……


3. 可访问性(可视性)控制

关注 HelloJava 类的第9行, 这里我们直接通过 p.name = "小花" 对对象 p 的内部属性进行了操作, 这事实上破坏了对象的"封装性", 这是不可取的! (参阅《面向对象起步 --- 封装、继承、多态》)
也就是说, 我们应尽可能地将对象的成员(属性/方法)封装在内部, 而不是随意地向外界暴露, 这才更符合封装的要求. 这就像你的私有财产总得藏着点, 不能随意让外人使用.

那么怎么把不想向外界暴露的成员藏起来呢? 这就要说到一个新的话题: 可访问性控制 (一些材料上也叫"可视性")
打开 Pig 类的源代码, 将 name 属性前的 public 修饰符改为 private, 代码如下:
private String name;
保存( Ctrl + S ) …… 之后我们注意到在 HelloJava 类的图标上出现了一个红色的叉, 这就说明出问题了……  切换到 HellowJava 类的代码视图(如下图), 把鼠标放在划红线的那里, 看看人家说什么了……

Java程序设计入门 (一) - bailey - Baileys Blog
  
大意是: Pig 类里的 name 属性(filed, 字段) 不可见! 也就是说, 在 HelloJava 的 main 方法中不能直接访问 name 属性了.
看出 private 修饰符的作用了吧~ 它把 name 属性变成私有的了, 藏起来了……

好的, 插播几个概念: 
在属性或方法的前面, 我们可以添加修饰符, 以控制属性或方法的可访问性(可视性). Java中有3种修饰符, 它们的作用如下:
private : 私有的, 只在当前类中可访问. 
protected : 被保护的, 只在当前类,  当前类的子孙类 (子孙后代), 以及与当前类同属一个包 (package)的其它类 中可访问.
public : 公有的, 在所有类中均可访问.

那么…… 如果不写任何修饰符时"可访问性"又是如何呢? 
这种情形下通常称作 default 修饰符, 它并不等同于 private, protected 或 public中的任何一个! 具体的差异可参看下表, 但不建议使用~
作为一个好的习惯, 建议在定义 类, 属性 和 方法 时都明确地为其加上可访问性修饰符!

 修饰符 当前类 同一包内 子孙类 其他包
 public √   
 protected    ×
 default   × ×
 private  × × ×
   

现在我们成功地把 name 属性私有化了, 所以外界怎么对它进行操作呢?
在Pig类中添加代码, 让它变成下面的样子:
  1: package com.bailey.study.animal;
  2: 
  3: public class Pig {
  4:     
  5:     private String name;
  6:     public String sex;
  7:     public void eat(String food) {
  8: 	      System.out.println(name + "吃了" + food);
  9:     }
 10:     
 11:     public void setName(String name) {
 12: 	      this.name = name;      // 在任何对象中, 代词 this 均指代当前对象
 13:     }
 14:     
 15:     public String getName() {
 16: 	      return name;
 17:     }
 18: }
我们为 Pig 类添加了2个方法: setName 和 getName. 
这两个方法使用 public 修饰, 这样外界就可以通过这两个方法对 name 属性进行操纵了. ( 相应地, 应该把HelloJava类中的 p.name = "小花" 改成 p.setName("小花"); )
这样做的好处是: 我们可以灵活控制外界对 name 属性的操纵, 例如: 当需要在设置 name 属性的值时做一些附加的操作, 就可以把代码写在 setName 方法中. 当然, 如果不想让外界取得name的值, 那把getName方法去掉就行了.
对于 setXXX, getXXX 这样的方法, 通常称为 setter 和 getter方法.

上面代码中第12行很有趣: this.name = name;
this.name 指的是当前对象的name属性 (在对象A中, this.name就是A的name属性, 在对象B中, 它就是B的name属性), 而 "=" 后面的 name 指的是setName方法的name参数.
这里的代词 this 并不指向某个特定对象, 它指向当前对象. 关于 this 还有另外一层意思, 请继续往下看, 在讲述"构造函数"时将会提及.
类似的, 还有一个代词: super, 它指向当前类的直接父类.

~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~

在华丽丽的分隔线之后, 我们讲本节的最后一个概念: 构造函数
所谓"构造函数"其实是一种特别的函数(方法), 它的名称与类名相同, 在实例化的时候构造函数将被首先执行. 
通常在构造函数中做一些初始化的工作.
现在在Pig类中添加一个方法, 代码如下:
public Pig(String name, String sex) {
    this.name = name;
    this.sex = sex;		
    System.out.println(name + "出生啦(Constructed)!");
}
这样就为Pig类添加了一个构造函数, 相应的, 在实例化时就应该传入所需的参数, 例如: Pig p = new Pig("小花", "雄"); 赶快试试吧~

与普通方法一样, 构造函数也可以重载. 试着再为Pig类添加一个构造函数, 代码如下:
  1: public Pig(String name) {
  2:   this(name, "未知");      // 调用之前定义那个构造函数
  3: }
注意一下第2行, 又见到代词 this 了. 在这里 this 特指当前类, 事实上第2行的写法就是告诉Java, 根据传入的参数去选择调用一个合适的构造函数.
把 HelloJava.java 中的 Pig p = new Pig("小花", "雄"); 改成 Pig p = new Pig("小花"); 设置断点, 跟踪调试一下吧~

关于构造函数, 还有几点需要注意:
(1) 当一个类中没有明确定义任何构造函数时会有一个默认的不带任何参数的构造函数, 类似这样:
public Pig() {
}
          而当我们明确地定义了任何一个或多个构造函数后, 上述默认的构造函数就不存在了.
(2) 若父类中未定义默认构造函数 (如: Pig(){ ... }, 则子类中必须至少明确定义一个构造函数. 并使用super(...) 调用父类构造函数. (若看不懂, 暂时放一下, 在学习到继承时就明白了)
(3) 若构造函数中出现了 this(...); 那么必须把它写在当前构造函数中的第1行. 

~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~

好了, 本节内容就是这些…… 

也许看完了之后你会发现有各种各样的规则(要求), 别忙着死记, 放轻松~ 事实上, Eclipse是很聪明的, 当你犯错时它会划红线提醒你的, 到时候再看看提示, 改一改就好了. 写了一些程序之后, 慢慢地就不会犯错了……

为了让你看上去像一个老Java程序猿, 一些约定俗成的东西应该遵循, 一些技巧可以了解:
(1) 定义类/属性/方法时记得为它们加上访问修饰符
(2) 包名首字母小写
(3) 类名采用首字母大写的驼峰命名规则(大Camel-Case)
(4) 属性名, 方法名采用首字母小写的驼峰命名规则(小Camel-Case)
(5) 输入代码的过程中, 使用Eclipse快捷键 Alt + / 可调出输入提示
(6) 在代码视图中点右键 → Source → Generate Getters and Setters ... 可快速地生成 getter, setter方法.
(7) 程序出现异常时, 善用调试(Debug)模式进行查错, 别动不动就怀疑是不是电脑出问题了, 或者抬嘴就问.

原文地址:https://www.cnblogs.com/toge/p/6114746.html