黑马程序员——Java基础---Java语言基础(二)

------- android培训java培训、java学习型技术博客、期待与您交流! ----------

第一讲 程序的流程控制

简述

       控制流程(也称为流程控制)是计算机运算领域的用语,意指在程序运行时,个别的指令(或是陈述子程序)运行或求值的顺序。不论是在声明式编程语言或是函数编程语言中,都有类似的概念。在声明式的编程语言中,流程控制指令是指会改变程序运行顺序的指令,可能是运行不同位置的指令,或是在二段(或多段)程序中选择一个运行。

1.判断结构 if语句

  • if语句的三种格式
    • if(true){ 执行语句 ;}
    • if(条件表达式){执行语句;} else{执行语句;}
    • if(条件表达式){执行语句;} else if(条件表达式){执行语句;}.... else{执行语句;}
  • if语句的特点
    • 每一种格式都是单条语句。
    • 第二种格式与三元运算符的区别:三元运算符运算完要有值出现。好处是:可以写在其他表达式中。
    • 条件表达式无论写成什么样子,只看最终的结构是否是true 或者 false;
2.选择结构 switch语句
  • 格式

switch(表达式)

{

case 取值1:

执行语句;

break;

case 取值2:

执行语句;

break;

…...

default:

执行语句;

break;

}

  • 原理
    • 用小括号中的变量的值依次和case后面的值进行对比,和哪个case后面的值相同了,就执行哪个case后面的语句,如果没有相同的则执行default后面的语句;
  • 特点
    • switch语句选择的类型只有四种:byte,short,int ,char。
    • case之间与default没有顺序。先执行第一个case,没有匹配的case执行default。
    • 如果将default语句放在了第一行,则不管expression与case中的value是否匹配,程序会从default开始执行直到第一个break出现。
    • 结束switch语句的两种情况:遇到break,执行到switch语句结束。
    • 如果匹配的case或者default没有对应的break,那么程序会继续向下执行,运行可以执行的语句,直到遇到break或者switch结尾结束。

3.循环结构 代表语句 for while do-while

  • for循环
    • 格式

for(初始化表达式;循环条件表达式;循环后的操作表达式)

{

执行语句;(循环体)

}

    • 特点
      • for里面的两个表达式运行的顺序,初始化表达式只读一次,判断循环条件,为真就执行循环体,然后再执行循环后的操作表达式,接着继续判断循环条件,重复找个过程,直到条件不满足为止。
    • 示例

for(int i = 0;i < 3;i++)

{

System.out.println(i);

}

  • while循环
    • 格式

while(条件表达式)

{

执行语句;

}

    • 特点
      • 先进行条件判断,再执行循环体。如果条件不成立,退出循环。
    • 示例

int x = 3;

while(x<5)

{

x++;

System.out.println(x);

}

  • do-while循环
    • 格式

do

{

执行语句;

}while(条件表达式);

    • 特点
      • 先执行循环体,再进行条件判断,循环体至少执行一次。

4.其他语句 break continue语句

  • break语句
    • 作用:用于switch ,和循环语句,用于跳出,或者称为结束。
    • 注意:break语句单独存在时,下面不要定义其他语句,因为执行不到,编译会失败。当循环嵌套时,break只跳出当前所在循环。要跳出嵌套中的外部循环,只要给循环起名字即可,这个名字称之为标号。
  • continue语句
    • 作用:只作用于循环结构,继续循环用的。结束本次循环,继续下次循环。
    • 注意:该语句单独存在时,下面不可以定义语句,执行不到。
5.语句的选择
  1. 当判断固定个数的值的时候,可以使用if,也可以使用switch。
  2. 但是建议使用switch,效率相对较高。
  3. 当判断数据范围,获取判断运算结果boolean类型时,需要用if。
  4. 当某些语句需要执行很多次,就用循环结构。
  5. while和for可以进行互换。区别在于:如果需要定义变量控制循环次数,建议使用for。因为for循环完毕,变量在内存中释放。

第二讲 函数

简述

为了提高代码的复用性,可以将其定义成一个单独的功能,该功能的体现就是java中的函数。函数就是体现之一。

  • Java中函数的定义格式

修饰符 返回值类型 函数名(参数类型 形式参数1,参数类型 形式参数1,…){

执行语句;

return 返回值;

}

    • 当函数没有具体的返回值时,返回的返回值类型用void关键字表示。
    • 如果函数的返回值类型是void时,return语句可以省略不写的,系统会帮你自动加上。
    • return的作用:结束函数。结束功能。
  • 如何定义一个函数,函数其实就是一个功能,定义函数就是实现功能,通过两个明确来完成:
    • 明确该功能的运算完的结果,其实是在明确这个函数的返回值类型。
    • 在实现该功能的过程中是否有未知内容参与了运算,其实就是在明确这个函数的参数列表(参数类型&参数个数)。
  • 函数的作用:
    • 用于定义功能。
    • 用于封装代码提高代码的复用性。
  • 函数的特点:
    • 函数只有被调用才会被执行。
    • 对于函数没有具体返回值的情况,返回值类型用关键字void表示,那么该函数中的return语句如果在最后一行可以省略不写。
    • 注意:函数中只能调用函数,不能定义函数。
  • 主函数:
    • 保证该类的独立运行。
    • 因为它是程序的入口。
    • 因为它在被jvm调用。
  • 函数定义名称是为什么
    • 为了对该功能进行标示,方便于调用。
    • 为了通过名称就可以明确函数的功能,为了增加代码的阅读性。
  • 函数的重载(overload)
    • 概念:在同一个类中,允许存在一个以上的同名函数,只要它们的参数个数或者参数类型不同即可。
    • 特点:与返回值类型无关,只看参数列表。
    • 好处:方便于阅读,优化了程序设计。
    • 示例:
/返回两个整数的和
  int add(int x,int y){return x+y;}
//返回三个整数的和
  int add(int x,int y,int z){return x+y+z;}
//返回两个小数的和

  double add(double x,double y){return x+y;}

第三讲 数组
简述
       数组(Array)是Java 语言中内置的一种基本数据存储结构,通俗的理解,就是一组数的集合,目的是用来一次存储多个数据。数组是程序中实现很多算法的基础,可以在一定程度上简化代码的书写。简单的说, 数组就是用于存储同一类型数据的一个容器。
  • 好处:可以对该容器中的数据进行编号,从0开始。数组用于封装数据,就是一个具体的实体。
  • 数组的声明:
    • type varName[]; 或 type[] varName;(推荐)
  • 数组的初始化:
    • 动态初始化:初始化时由我们指定数组的长度,由系统为数组元素分配初始值。
      • 格式:元素类型[] 变量名 = new 元素类型[元素的个数];
        • 示例:int[] arr = new int[5];
    • 静态初始化:初始化时由我们自己指定每个数组元素的初始值,由系统决定需要的数组长度。
      • 格式:
        1. 元素类型[] 变量名 = {元素1,元素2...}; 
        2. 元素类型[] 变量名 = new 元素类型[]{元素1,元素2...};
        • 示例:int[] arr = {4,5,9,7};  int[] arr = new int[]{2,5,1,7};
  • 特点:
    • 数组必先初始化才可以使用。
    • 数组是固定长度的。
    • 数组可以存储基本数据类型,也可以存储引用数据类型。
    • 数组存储的元素必须是同一个数据类型。
  • 二维数组
    • 其实是一个一维数组,它的每一个元素又是一个一维数组。
    • 声明:
      • type varName[][]; type[][] varName;(推荐)
    • 动态初始化:
      • int[ ][ ]  arr = newint[2][3];
    • 静态初始化:
      • int[ ][ ]  arr = new int[][]{{1,2},{3,4},{5,6}};
      • int[ ][ ]  arr ={{1,2},{3,4},{5,6}};

内存结构

    Java程序在运行时,需要在内存中的分配空间。为了提高运算效率,有对空间进行了不同区域的划分,因为每一片区域都有特定的处理数据方式和内存管理方式。

  • 栈内存
    • 用于存储局部变量,当数据使用完,所占空间会自动释放。
  • 堆内存
    • 数组和对象,通过new建立的实例都存放在堆内存中。
    • 每一个实体都有内存地址值。
    • 实体中的变量都有默认初始化值。
    • 实体不在被使用,会在不确定的时间内被垃圾回收器回收。
  • 方法区,本地方法区,寄存器
数组的内存结构图

  • 一维数组内存结构

黑马程序员——Java基础---Java语言基础(二)_第1张图片

  • 二维数组内存结构

黑马程序员——Java基础---Java语言基础(二)_第2张图片

  • 数组操作常见问题
    • 数组脚标越界异常(ArrayIndexOutOfBoundsException)
int[] arr = new int[2];
System.out.println(arr[3]);

访问到了数组中的不存在的脚标时发生。

    • 空指针异常(NullPointerException)

int[] arr = null;

System.out.println(arr[0]);

arr引用没有指向实体,却在操作实体中的元素时。

数组的常见操作

  • 获取最值(最大值、最小值)
    • 这里简单写下获取最大值
public class ArrayTest {
	public static void main(String[] args) {
		// TODO Auto-generated method stub
		int [] arr = {4,6,8,3,18,9,17};
		System.out.println(getMax(arr));
		System.out.println(getMax_2(arr));
	}

	    //获取数组中最大值
		/*
		 * 思路:
		 * 1,获取最值需要进行比较,每一次比较都会有一个较大的值,因为值不确定,
		 * 		通过一个变量进行存储。
		 * 2,让数组中的每一个元素都和这个变量的值进行比较。
		 *       如果大于了变量中的值,就用该变量记录较大值。
		 * 3,当所有的元素都比较完成,那么该变量中存储的就是数组中的最大值。
		 * 
		 *   步骤:
		 *   
		 *   1,定义变量,初始化为数组中任意一个元素即可。
		 *   2,通过循环语句对数组进行遍历。
		 *   3,在遍历过程中定义判断条件,如果遍历到的元素比变量中的元素大,
		 *         就赋值给该变量。
		 *  
		 *  需要定义一个功能来完成,以便提高复用性。
		 *1,明确结果,数组中的最大元素 int...
		 *2,位置内容:一个数组 int[]
		 * */
		
		public static int getMax(int[] arr)
		{
			int max = arr[0];
			for(int x = 1 ; x< arr.length;x++)
			{
				if(arr[x] > max)
				{
					max = arr[x];
				}
			}
			return max;
		}
		public static int getMax_2(int[] arr)
		{	
			int max = 0;
			for(int x = 1 ; x< arr.length;x++)
			{
				if(arr[x] > arr[max])
				{
					max =x;
				}
			}
			return arr[max];
		}
}


  • 排序(选择排序,冒泡排序)
    • 选择排序
      • 原理:先用0角标上的元素依次与其他元素进行比较,将较小值元素存放到0角标。然后再拿1角标上的元素依次进行比较,以此类推。
      • 特点:内循环结束一次,最值出现在头角标位置上。
      • 原理图解:
黑马程序员——Java基础---Java语言基础(二)_第3张图片
    • 冒泡排序
      • 原理:
        • 先从头角标相邻两个元素之间进行比较,将最值存放在后一个元素中,然后再与后一个元素的进行比较,直至最值存放到最后一个元素中。再从1角标开始再重复以上操作,每次计较次数减一,一圈比完后存放的最值元素不再参与比较。
      • 特点:内循环结束一次,最值出现在尾角标位置上。
      • 原理图解:

黑马程序员——Java基础---Java语言基础(二)_第4张图片

    • 排序小练习
public class ArrayTest {
	public static void main(String[] args) {
		// TODO Auto-generated method stub
		int [] arr1 = {4,6,8,3,9,17};
		selectSort(arr1);
		printArray(arr1);
		int [] arr2 = {10,7,8,5,9,6};
		bubbleSort(arr2);
		printArray( arr2);
	}
	/*
	 * 选择排序
	 * 内循环结束一次,最值出现在头角标位置上
	 * */
	public static void selectSort(int[] arr)
	{
		//用一个外循环控制每次用哪个角标与后面的元素进行比较
		for(int x = 0 ; x< arr.length -1;x++)
		{
			 //用一个内循环使选定的元素与它后面的每个元素进行比较换位
			for(int y= x+ 1 ; y< arr.length;y++)
			{
				if(arr[x] > arr[y])
				{
					int  temp = arr[x];
					arr[x]  = arr[y];
					arr[y] = temp;
				}
			}
		}
		
	}
	
	/*
	 * 冒泡排序
	 * 特点 内循环结束一次,最值出现在尾角标位置上
	 * */
	public static void bubbleSort(int[] arr)
	{
		for(int x = 0 ; x< arr.length -1;x++)
		{
			//y< arr.length - x -1防止角标越界
			//-x目的:让每一次比较的元素减少
			//-1目的:避免角标越界
			for(int y= 0 ; y< arr.length - x -1;y++)
			{
				if(arr[y] > arr[y+1])
				{
					int  temp = arr[y];
					arr[y]  = arr[y+1];
					arr[y+1] = temp;
				}
			}
		}
	}
	
    //遍历数组  
    public static void printArray(int[] arr)  
    {  
        System.out.print("[");  
        for (int x=0;x
  • 折半查找(二分查找)
    • 前提:数组中元素必须是有序的。
    • 原理:
      1. 定义两个变量,一个初始化0角标,作为最小值,一个初始化为最后角标,作为最大值,再定义一个变量,存储最小值与最大值的一半,也就是中间位置,然后将要查找的元素与中间值位元素进行比较。
      2. 如果比中间值元素大,则将最小值变为中间值加1,继续取最小值与最大值的中间值元素与要查找元素进行比较,以此反复。
      3. 如果比中间值元素小,则将最大值变为中间值减1,继续取最小值与最大值的中间值元素与要查找元素进行比较,以此反复。 
    • 练习:
public class HalfSeachDemo {
	/**
	 * 需求:将一个已知元素插入到一个有序数组中,要求不改变数组顺序,打印元素应该插入数组位置的角标。
	 * 思路:因为数组是有序的,可以使用二分查找,查找到插入元素在数组中的位置。
	 * @param args
	 */
	
	public static void main(String[] args) {
		 int[] arr={6,9,11,17,23,31};  
	     //打印数组  
		 printArray(arr);  
		 //用第一种折半方式输出插入的角标值 
	     System.out.println("25插入数组中的位置:" + halfseach_1(arr,25));
	     //用第二种折半方式输出插入的角标值 
	     System.out.println("15插入数组中的位置:" + halfseach_2(arr,15));
	}
	public static int halfseach_1(int [] arr , int key)
	{
		int min,max,mid;
		min = 0 ;
		max = arr.length-1;
		mid = (max+min)/2;
		while(key != arr[mid] )
		{
			if(min>max)  
                return min;  
            else if(key>arr[mid])  
                min=mid+1;  
            else   
                max = mid - 1;  
			mid = (max + min)/2;
		}
		return mid;
	}
	
	public static int halfseach_2 (int [] arr , int key)
	{
		int min,max,mid;
		min = 0 ;
		max = arr.length-1;
		mid = (max + min)/2;
		while(min <= max)
		{
			mid = (max + min)/2;
			if(key > arr[mid])
				min = mid+1;
			else if(key< arr[mid])
				max = mid - 1;
			else 
				return mid;
		}
		return min;
	}
	//遍历数组
	public static void printArray(int[] arr)
	{
		System.out.print("[");  
		for (int i = 0; i < arr.length; i++) {
			if(i != arr.length - 1)
				System.out.print(arr[i] + ",");
			else
				System.out.println(arr[i] + "]");
		}
	}	
}



------- android培训java培训、java学习型技术博客、期待与您交流! ----------

你可能感兴趣的:(Java)