循环语句
java中的主要的循环语句分为3种:for循环,while循环,do-while循环;
1)for循环
它的表达式是for(初始化语句;条件表达式;控制体语句){
循环体;
}
它的执行顺序是;先初始化语句,再执行条件表达式,表达式成立,执行循环体,再执行控制体语句;然后继续判断条件表达式,执行循环体,如此循环下去;表达式不成立则直接结束for循环.
采用for循环时,是已知循环次数的.
for循环可以嵌套使用来完成许多操作,如生成一个m行n列的*型(外层循环控制行,内层循环控制列),或一个m行n列的乘法口诀表...
2)while循环
它的表达式是while(条件表达式){
循环体;
控制体语句;
}
执行顺序是先判断条件表达式是否成立,若成立,执行循环体,再执行控制体语句,然后再次判断条件表达式,如此循环;若表达式不成立,则结束while循环.
采用while循环时,一般不明确它的循环次数.
for循环与while循环小节:
for循环中初始化的条件在for循环结束后不能访问了,变量立刻被释放,节省内存,而whlie循环结束后,变量仍然可以被访问到.比较占内存.
3)do-while循环
它的表达式是do{
循环体语句;
控制体语句;
}while(条件表达式);
do-while循环一般在开发中较为少用,优先可以采用前两种循环,
他的执行顺序是,先执行一次循环体语句,然后控制体语句,最后判断条件表达式,也就是说即使条件不成立,他也会执行一次循环体语句!
跳转控制语句
跳转控制语句有break,return,continue.
break: 是结束中断或循环(不能单独使用)一般用于switch和循环中.
continue: 是结束本次循环,进入下一次循环,一般也是应用于循环中.
return: 一般用于结束某个方法,返回一个值时使用.
方法
在java中,为了使main函数层次清晰明了,可以将实现某些功能的函数使用{}打包,起一个名字独立到主函数外面,在主函数中需要用到它时通过调用的方法实现其中的功能,这就是方法的定义,可以理解为子函数,它的格式如下
public static 返回值 方法名(变量类型1 变量名,变量类型2 变量名...){
被打包的代码;
return 结果;(若为空返回类型,则无return)
}
若是有参的方法,则()内的形参变量类型必须声明.
返回值分为两种,有返回值和无返回值.
若有返回值,返回值处声明返回值的类型,也就是目前使用的基本数据类型,在函数的结尾使用return 结果来结尾.
需要调用时,则需在主函数中写上方法名(参数1,参数2...),必须和所要调用的子函数中的参数个数及参数类型对应;由于有返回值类型的方法会得到一个值,所以可以使用赋值调用和直接输出的手段得到它.即:
1)赋值调用: 变量类型 变量名 = 方法名(参数1,参数2...); 推荐使用该方法.
2)输出调用: System.out.println(方法名(参数1,参数2...));
若无返回值,使用viod替代.调用时选择直接调用的方法.
3)直接调用: 方法名(参数1,参数2...);
方法重载(overload)
方法重载就是:方法名相同,参数列表不同,与返回值无关,与public也无关,
也就是判断时只看他们的方法名是否相同.
方法重载的目的:为了提高某个功能的扩展性,在有的时候,同一个方法,可以传递任何数据类型.
数组
数组就是存储多个相同类型数据的容器.
数组的定义格式分为:
1)静态初始化: 数据类型[] 数组名 = new 数据类型[]{a,b,c,d....};
可简写为: 数据类型 数组名[] = {a,b,c,d...};
[]中括号可以在数据类型后也可以跟在数组名后.
2)动态初始化: 数据类型[] 数组名 = 数据类型[数组长度];
如 int arr[] = new int[3];
arr[0] = 4;
arr[1] = 3;
arr[2] = 2;
我们不赋值的话,系统默认给他赋值0.
需要注意的是,不可以以此类方式初始化: int arr [] = new int[3]{1,2,3};
下面是将数组录入,遍历,排序,搜索索引值使用方法的方式得到:
import java.util.Scanner;
class haha {
public static void main(String[] args) {
int[] arr = new int[5];
Scanner sc = new Scanner(System.in);
for (int i = 0; i <= arr.length - 1; i++) {
System.out.println("请输入一个数:");
int a = sc.nextInt();
arr[i] = a;
}
array(arr);
mp(arr);
array(arr);
System.out.println("输入你想寻找的数字:");
int b = sc.nextInt();
System.out.println("它的index是:"+find(arr,b));
}
public static void array ( int[] arr){
System.out.print("[");
for (int i = 0; i <= arr.length - 1; i++) {
if (i == arr.length - 1) {
System.out.println(arr[i] + "]");
} else if (i < arr.length - 1) {
System.out.print(arr[i] + ",");
}
}
}
public static void mp ( int arr[]){
for (int i = 0; i < arr.length - 1; i++) {
for (int j = 0; j < arr.length - 1 - i; j++) {
if (arr[j] > arr[j + 1]) {
int temp = arr[j];
arr[j] = arr[j + 1];
arr[j + 1] = temp;
}
}
}
}
public static int find(int [] arr,int a){
for(int i = 0;i < arr.length;i++){
if ( a == arr[i]){
return i;
}
}
return -1;//返回-1是找不到该数,即输入的数字非法.
}
}
方法中的形参问题
1)形参为基本数据类型: 形参的改变不会影响实际参数.例如
class haha{
public static void main(String[] args) {
int a = 1;
int b = 2;
System.out.println("a="+a+",b="+b);
change(a,b);
System.out.println("a="+a+",b="+b);;
}
public static void change(int a ,int b){
System.out.println("a="+a+",b="+b);
a = b;
b = a + b;
System.out.println("a="+a+",b="+b);
}
}
结果是:
a=1,b=2
a=1,b=2
a=2,b=4
a=1,b=2
Process finished with exit code 0
2)形参为引用数据类型: (String类除外,String的本质是常量,所以他的改变不会影响实参.)String举例:
class haha{
public static void main(String[] args) {
String a = "hello";
System.out.println("a="+a);
change(a);
System.out.println("a="+a);
}
public static void change(String a){
System.out.println("a="+a);
a += "java";
System.out.println("a="+a);
}
}
结果是:
a=hello
a=hello
a=hellojava
a=hello
Process finished with exit code 0
形参的改变会影响实参.例如
class haha{
public static void main(String[] args) {
int arr[] = {1,2,3};
array(arr);
change(arr);
array(arr);
}
public static void change(int arr[]){
array(arr);
arr[0] += 1;
arr[1] += 1;
arr[2] += 1;
array(arr);
}
public static void array(int arr[]){
System.out.print("[");
for(int i= 0;i < arr.length;i++){
if(i == arr.length-1){
System.out.println(arr[i]+"]");
}else if(i < arr.length){
System.out.print(arr[i]+",");
}
}
}
}
结果是:
[1,2,3]
[1,2,3]
[2,3,4]
[2,3,4]
Process finished with exit code 0
造成这个现象的原因是: 基本数据类型的创建和使用都是在栈内存中,他会随着方法的结束而立刻消失,即自动被释放,
而引用数据类型如数组: 数组是在栈中开辟内存空间,在堆内存中存放具体的数组内容.在栈中数组放的是一个地址值,该地址会指向堆内存中数组的具体内容,由于堆内存的清理缓存的方式是等待GC回收器处理.所以数组中的内容不会立刻消失,所以形参的改变会影响到实际参数.
面向对象
面向对象举例: 如在生活中我需要买东西,而买东西我需要出门,制定路线,到地点,找商品.....最后买到东西而现在出现了一个人,他可以帮我们执行买东西这一复杂的操作,我们只需要告诉这个人,我要买东西,然后他去买,最后我得到东西.这个人就是对象.其中对象执行的过程就是面向过程.
面向对象的特点是: 1) 更加符合我们的生活习惯 2) 让复杂的事情简单化 3) 让我们从执行者变成了指挥者.
面向对象的三大特征: 封装,继承,多态.
面向对象的设计理念: 不断地创建对象,使用对象,指挥对象做事情.如Scanner.
类与对象的关系
类是对象的抽象,而对象是类的具体实例。类是抽象的,不占用内存,而对象是具体的,占用存储空间。
什么是类?
类是能够描述现实世界真实事物的一组属性和行为的集合.我们需要将现实世界的事物的属性和行为通过java语言表示出来.在java中类是最基本的单元.
类的基本写法
class 名称{
成员变量;如 String name;
成员方法;如 public static void play(String game){
System.out.println("玩"+game);
}
构造方法;public 名称(与类名相同)(String name){
this.name = name;
}
}
创建完类后需要在其他类中创建对象类来访问该类中的成员,具体格式如程序中所示
class shuxing{
String name;// 成员变量 name 和 gender
String gender;
public static void play(String game){//成员方法
System.out.println("玩"+game);
}
}
class person{
public static void main(String[] args) {
shuxing a1 = new shuxing();//创建对象
shuxing a2 = new shuxing();//创建对象
a1.name = "李明";//访问姓名.
a2.name = "张明";
System.out.print(a1.name+"喜欢");
a1.play("lol");//访问方法
System.out.print(a2.name+"不喜欢");
a2.play("游戏");
}
}
运行结果:
李明喜欢玩lol 张明不喜欢玩游戏
Process finished with exit code 0
如果一个方法的参数是引用类型---类,该怎么访问?
class lei{
public void play(){
System.out.println("wan游戏");
}
}
class gap{
public void playg(lei p){
p.play();
}
}
class gapd{
public static void main(String[] args) {
gap a = new gap();
lei b = new lei();// 需new一个访问lei的对象
a.playg(b);//得到lei中成员方法play的值.
}
}
匿名对象
匿名的对象就是没有名字的对象.
它的格式: new 类名();
匿名对象的特点: 可以作为参数进行传递,在开发中,匿名对象使用一次即可,匿名对象是直接在堆中开辟空间来使用,使用完毕直接被回收.
适用场景: 由于其不在栈中开辟空间, 减少了内存占用, 所以在内存较小的如手机app经常被使用
封装
由于我们定义的数据(public)可以被随意修改,现在可以使用权限修饰词private将属性隐藏.被private修饰的属性只能通过本类中给出的公共访问方式来访问.具体方式如下:
class n1{
private String name;//封装成员变量
private void play(){//封装方法
System.out.println("玩游戏");
}
public void big(){
play();
}
public void setname(String name){
this.name = name;//this.成员变量 = 形参;
}
public String getname(){
return name;
}
}
class student{
public static void main(String[] args) {
n1 a = new n1();
a.setname("李明");
System.out.print("学生"+a.getname()+"喜欢");
a.big();
}
}
输出结果是:
学生李明喜欢玩游戏
Process finished with exit code 0
构造方法
构造方法就是没有具体返回值类型的方法,它的方法名与类名一致.
构造方法有什么用?
用来给类中一个或多个成员进行初始化,方便赋值.
构造方法分为有参和无参两种,本节之前我使用的都是无参构造.当我们书写某个类中代码的时候,没有给这个类提供任何构造方法,那么系统会默认提供一个无参构造方法.如果你同时使用了有参构造和无参构造,系统不在会为你默认提供一个无参构造方法,这时你需要手动给出这个方法.
class shuxing{
String name;
String gender;
public shuxing(){//手动给出无参构造方法.
}
public static void play(String game){
System.out.println(",玩"+game);
}
public shuxing(String name,String gender){
this.name = name;
this.gender = gender;
}
}
class person{
public static void main(String[] args) {
shuxing a1 = new shuxing("李明","男");
shuxing a2 = new shuxing();
System.out.print(a1.name+",性别:"+a1.gender);
a1.play("genshin");//结果是: 李明,性别:男,玩genshin
}
}
如果将无参方法注掉,将会得到error
Error:(18, 22) java: 无法将类 shuxing中的构造器 shuxing应用到给定类型; 需要: java.lang.String,java.lang.String 找到: 没有参数 原因: 实际参数列表和形式参数列表长度不同
所以在以后的使用中,我们1都手动给出这个无参构造方法,方法名需和类名相同.
public 方法名(){
}
无参构造方法和有参构造方法同时应用代码如下:
class canshu{
private int chang ;
private int kuan ;
public canshu(){}
public canshu(int chang,int kuan){
this.chang = chang;
this.kuan = kuan;
}
public void setchang(int chang){
this.chang = chang;
}
public int getchang(){
return chang;
}
public void setkuan(int kuan){
this.kuan = kuan;
}
public int getkuan(){
return kuan;
}
public int s(){
return chang*kuan;
}
public int c(){
return (chang+kuan)*2;
}
}
class a{
public static void main(String[] args) {
canshu a = new canshu(10,20);
canshu b = new canshu();
System.out.println("a的S="+a.s());
System.out.println("a的c="+a.c());
System.out.println("----------------------------------");
b.setchang(10);
b.setkuan(10);
System.out.println("b的S="+b.s());
System.out.println("a的c="+b.c());
}
}
得到结果为
a的S=200
a的c=60
----------------------------------
b的S=100
a的c=40
Process finished with exit code 0