您的位置:首页 > 职场人生

黑马程序员---流程控制,函数,数组

2015-06-29 13:46 731 查看
-----------android培训java培训、java学习型技术博客、期待与您交流!---------

判断结构

if语句

if语句的格式有三种:

1. if(条件表达式) {

执行语句;
}

2. if(条件表达式){

执行语句;

} else {

执行语句;

}

3. if(条件表达式){

执行语句;

} else if(条件表达式){

执行语句;

}

.........................

else{

执行语句;

}

注:在if语句中已有一行执行语句时可不写{ },

如果没有{ }那么if是控制离他最近的单条语句。

其中if else可以简写为三元运算符,

但因为是运算符,所以运算完必须要有结果。

选择结构

switch语句

格式:

switch(表达式) {

case 取值1:

执行语句;

break;

case 取值2;

执行语句;

break;

...

default:

执行语句;

break;

}

特点:

1. switch语句选择的类型只有四种:

byte,short,int,char。

2. case之间与的default没有顺序,

先执行第一个case,没有匹配的case执行default。

3. 结束switch语句有两种情况:

遇到break;执行到switch语句结束。

4. 如果匹配的case或default没有对应的break,

那么程序会继续向下执行,执行可执行的语句,

直到遇到break或switch结尾结束。

if和switch的区别

如果判断的数值不是很多,

而且符合byte,short,int,char这四种类型,

建议使用switch语句,因为效率稍高。

对于区间的判断,对结果为boolean类型的判断,

要使用if,if的范围更广一些。

循环语句

代表语句:while,do while,for

while循环语句格式:

while(条件表达式) {

执行语句;

}

特点:先判断条件,只有条件满足才执行循环体。

do while循环语句格式:

do{

执行语句

}while(条件表达式);

特点:无论是否满足条件,循环体至少被执行一次,

限制性循环体,在判断条件,条件满足再继续执行循环体。

for循环语句格式:

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

执行语句;

}

特点:简化程序,定义的变量只有在语句中存在,


语句结束就会在内存中释放,相对于while节省内存。


注:1. for里面的两个表达式运行的顺序,

初始化表达式只读一次,判断循环条件。

为真就执行循环体,然后再执行循环后的操作表达式,

接着继续判断循环体,重复整个过程,直到条件不满足为止。

2. while与for可以互换,

区别在于for为了循环而定义的变量在for循环结束后就在内存中释放,

而while循环使用的变量再循环结束后还可以继续使用。

3. 最简单无限循环格式:while(true),for(; ;)

无限循环存在的原因是并不知道循环多少次,

而是根据某些条件来控制循环。

while和for的区别:(初始化动作在外面)

1. 变量有自己的作用域,对于for来讲:

如果将用于控制循环的增量定义在for语句中,

那么该变量只在for语句内有效,for语句执行完毕,

该变量在内存中释放。

2. for和while可以进行互换,

如果需要定一循环增量,用for更合适。

总结:当需要对某些语句执行很多次时,就使用循环语句。

一定要明确哪些语句参与运算。

对于变量来讲,如果变量仅仅用于控制循环的次数,

的情况下用for(在内存上可以相对优化一点)。

其中条件表达式必须要有真假才能运行通过,

for循环不一定要用初始化表达式,

只要是合法的就可以。

对于for来说不写条件表达式默认为true。

嵌套循环

就是循环中还有循环

外循环执行一次到内循环,内循环执行完,外循环再执行一次到内循环。

格式:

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

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

执行语句;

}

}

while(条件表达式) {

while(条件表达式) {

执行语句;

}

}

总结:嵌套循环是外循环条件成立执行一次,内循环必须执行到条件不满足才结束。

累加思想原理:


通过变量记录住循环操作的结果,



通过循环的形式进行累加动作。


计数器思想:


通过一个变量记住数据的状态变化,



也许通过循环完成。


大圈套小圈的思想:

尖朝上改变条件,尖朝下改变初始值。

其他流程控制语句

break(跳出):应用于选择结构和循环结构。

continue(继续):应用于循环结构。

注:1. 这两个语句离开应用范围, 存在是没有意义的。

2. 这两个语句单独存在下面都不可以有语句,因为执行不到。

3. continue语句是结束本次循环接续下次循环。

4. 标号的出现,可以让这两个语句作用于指定的范围。 标号就是给循环语句前加一个名字,如:

a:for(; ;) 标号只能用于循环

练习:

尖朝下的星星:

/**
练习一
尖朝下的三角
*****
****
***
**
*

*/

class ForForDemo
{
public static void main(String[] args)
{
//外循环定义行数,题意是5行,所以x要小于等于5
for(int x=1;x<=5;x++)
{
//内循环定义每一行*的个数
for(int y=x;y<=5;y++)
{
//因为是要把*排成一行,所以不需要ln换行
System.out.print("*");
}
//内循环写完一行之后要换行写下一行
System.out.println();
}
}
}


运行结果



等腰三角形:

/*
练习二
等腰三角形
*
* *
* * *
* * * *
* * * * *

**/

class ForForTest2
{
public static void main(String[] args)
{
//外循环控制行数
for(int x=0;x<5;x++)
{
//内循环控制每行的个数
//空格相当于一个空格组成的倒三角,所以也需要循环输出
for (int y=x;y<4 ;y++ )
{
System.out.print(" ");
}
//空格已经占了前面的位置了,*直接输出就好,*中间还有空格,所以输出"* "
for (int z=0;z<=x ;z++ )
{
System.out.print("* ");
}
//换行
System.out.println();
}
}
}


运行结果



九九乘法表:
/**
练习三
打印九九乘法表
*/

class  ChengFaBiao
{
public static void main(String[] args)
{
//外循环控制了行数,九九乘法表,所以为九行
for(int x=1;x<=9;x++)
{
//内循环控制了每一行的个数,因为是尖朝上,改变条件
for(int y=1;y<=x;y++)
{
//输出乘法表内容,\t是制表符,让结果看起来更加清晰
System.out.print(y+"*"+x+"="+x*y+"\t");
}
//换行
System.out.println();
}
}
}


运行结果



函数

函数就是定义在类中的, 具有特定功能的一段小程序,函数也称为方法。

函数的格式:

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

执行语句;

return 返回值;

}

返回值类型:函数运行后的结果的数据类型。

参数类型:是形式参数的数据类型。

类型参数:是一个变量,用于存储和调用函数时,传递给函数的实际参数。

return:用于结束函数。

返回值:该值会返回给调用者。

函数的作用:

因为获取不同的运算结果,代码出现了重复,

为了提高代码的复用性,对代码进行抽取,

将这个部分定义成一个独立的功能,方便于日后使用。

Java中对功能的定义是通过函数的形成来体现的。

函数的特点:

定义函数可以将功能代码进行封装,便于对功能进行复用。

函数只有被调用才会被执行,函数的出现提高了代码的复用性,

对于函数没有具体的返回值情况,返回值类型用关键字void表示。

该函数中的return语句如果在最后一行可以省略不写。

函数的应用

如何定义一个函数?

1. 既然函数是一个独立的功能,

那么该功能的运算结果是什么先明确,

2. 在明确在定义该功能的过程中是否需要未知的内容参与运算。

其实这两个功能就是在明确函数的定义:

a. 是在明确函数的返回值类型。

b. 明确函数的参数列表(参数列表:参数类型和参数的个数)

定义函数时需注意:

1. 功能中只定义所需内容,不是该功能所需的内容不要定义。

2. 不要将代码都定义在主函数中。

3. 主函数的作用是:对已有的功能的进行调用,可以理解为用于功能的测试。

4. 函数名就是一个自己定义的标示符。函数名的定义,要尽量体现出这个函数的功能。是为了增强该函数的阅读性,

方便于调用者使用,所以函数名一定要有起的有意义。

5. 静态方法只能调用静态方法。主函数是静态的。

6. 返回值类型和参数类型没有直接关系。

注:1. 如果返回值是void类型,则不能在函数外的输出语句输出,直接调用就可。


2. 定义函数只要完成相对应的功能即可,只需把结果给调用者,
对于是否打印结果,是调用者的事,不要再函数内完成。

3. 函数中只能调用函数,不可以在函数内部定义函数。

函数的重载(overload)

重载的概念:

在同一个类中允许存在一个以上的同名函数,

只要他们的参数个数或者参数类型不同即可。

重载的特点:

与返回值类型无关,只看参数列表。

重载的好处:

刚便于阅读,优化了程序设计。

什么时候使用重载?

当定义的功能相同,但参与运算的未知内容不同,

那么这时就定义一个函数名称以表示其功能,方便阅读,

而通过参数列表的不同,来区分多个同名的函数。


理解:重载可以代表一种算法,如:把所有的和运算定义的方法都用同一个函数名,


利用所加个数的不同来区分所调用的方法。但如果重载中每个方法的参数类型不一样,

在调用函数是参数的顺序不能变。如:int abc(int x,int y)和int
abc(double x,int y),


在调用函数时参数的顺序不能变,才能进行有效的调用。

数组

概念:同一种类型数据的集合。其中数组就是一个容器。

好处:可以自动给数组中的元素从0开始编号,方便操作这些元素。

对数组的操作就是存和取。核心思想就是基于角标。

格式:

1. 元素类型[ ] 数组名 = new元素类型[元素个数或数据长度];

例:int[ ] arr = new int [ 5 ];

2. 元素类型[ ] 数组名 =元素类型[ ]{元素,元素......};

例:int[ ] arr = new int[ ]{3,5,2,1};

int[]arr = {3,5,2,1};

new:用来在内存中产生一个容器实体。

内存结构

Java在运行时,需要在内存中分配空间,为了提高运算效率。

对空间进行了不同的区域的划分, 因为每一片区域都有特定的处理数据的方式和内存管理方式。

栈内存:

用于存储内部变量,当数据使用完,所占空间会自动释放。

堆内存:

数组和对象通过new建立的实例都存放在堆内存中,

每一个实体都有内存地址值。

实体中的变量都有默认初始化值,实体不再被使用。

会在不确定的时间内被垃圾回期回收

在内存中还存在,方法区,本地方法区,寄存器。

栈内存,堆内存的区别就是处理方式不一样。

数组和对象只要是new的,都在堆内存中。



数组的常见操作

1. 获取数组中的元素。

可以通过元素的角标位获取,如要获取int数组arr中的第一个元素

int x = arr[0];

2. 获取最值。

3. 排序(冒泡排序,选择排序)。

4. 查找(折半查找只针对有序数组)插入元素(针对有序数组)。

注:数组中有一个属性可以直接获取数组元素的个数,length。

使用方式:数组名称.length arr.length获取数组中的元素个数。

获取数组中的元素:

/*
获取数组的中的元素

在这里我们就定义一个方法,专门用于获取int类型数组元素
*/
class  ArrayDemo1
{
public static void main(String[] args)
{
//定义数组
int[] arr = new int[]{5,8,5,6};

//调用输出数组中元素的方法
printArray(arr);
}
//定义输出数组中元素方法
public static void printArray(int[] arr)
{
//遍历数组,利用length获取数组长度,作为循环条件。
for(int x = 0 ; x<arr.length ; x++)
{
//输出数组中元素
System.out.println(arr[x]);
}
}
}


运行结果



获取最大值:

/*
获取数组中的最大值

定义一个方法用于获得int类型数组的最大值
*/
class  ArrayDemo2
{
public static void main(String[] args)
{
//定义数组
int[] arr = new int[]{4,8,46,1,58,1};

//调用获取最大值的方法,获取arr数组的最大值
int max = getMax(arr);

//输出最大值
System.out.println("Max = "+max);
}
//定义获取最大值的方法
public static int getMax(int[] arr)
{
//定义一个int类型变量max,让它等于arr[0]
int max = arr[0];

//遍历数组
for(int x=0 ; x<arr.length ; x++)
{
//判断arr[x]是否大于max
//如果arr[x]大于max 那就把它的值赋给max
if(arr[x]>max)
max = arr[x];
}
//最后返回max的值
return max;
}
}


运行结果



给数组中的元素排序

选择排序:

/*
给数组排序——————选择排序
*/
class  ArrayDemo3
{
public static void main(String[] args)
{
//定义要被排序的数组
int[] arr = new int[]{654,657,5,7,859,54,5};

//调用排序方法
arraySort(arr);

//排序完再调用输出方法,输出数组
printArray(arr);
}
//选择排序方法
public static void arraySort(int[] arr)
{
//创建内循环,让数组中的每一个元素都可以去和数组中其他元素进行比较
//外循环控制拿来比较的元素的个数,循环条件-1是因为最后一个数就不用比了,别人都跟它比完了
for(int x=0 ; x<arr.length-1 ; x++)
{
//内循环控制比较
for(int y=x+1 ; y<arr.length ; y++)
{
//判断数组中的一个元素是否大于另一个元素
if(arr[x]>arr[y])
//如果是,调换它俩的顺序,小的在前
//调用通过角标位置换元素方法
swap(arr,x,y);
}
}
}
//通过角标位置换元素方法
public static void swap(int[] arr , int a , int b)
{
//定义一个int类型变量,接收arr数组a角标位上的元素
int i = arr[a];

//将b角标位上元素赋给a角标位
arr[a] = arr[b];

//将i变量接受的数,赋给b角标位
arr[b] = i;
}
//定义输出数组中元素方法,输出结果更加高级!
public static void printArray(int[] arr)
{
System.out.print("[");
//遍历数组
for(int x=0;x<arr.length;x++)
{
//如果x不是数组角标的最后一位
if(x!=arr.length-1)
//按这个语句输出,后面带 ,
System.out.print(arr[x]+", ");
//如果是数组的最后一位
else
//就按这个语句输出,后面带中括号
System.out.println(arr[x]+"]");
}
}
}


运行结果



冒泡排序:

/*
给数组排序——————冒泡排序
*/

class ArrayDemo4
{
public static void main(String[] args)
{
//定义要被排序的数组
int[] arr = new int[]{4,8,54,7,9,1,3};

//调用排序方法
arraySort(arr);

//排序完再调用输出方法,输出数组
printArray(arr);
}
//定义数组的冒泡排序方法
public static void arraySort(int[] arr)
{
//创建内循环,让数组中的每一个元素都可以去和数组中其他元素进行比较
//外循环控制拿来比较的元素的个数,循环条件-1是因为最后一个数就不用比了,别人都跟它比完了
for(int x=0 ; x<arr.length-1 ; x++)
{
//内循环控制比较
for(int y=0 ; y<arr.length-x-1 ; y++)
{
//判断数组中的前一个元素是否大于后一个元素
if(arr[y]>arr[y+1])
//如果是,调换它俩的顺序,小的在前
//调用通过角标位置换元素方法
swap(arr,y,y+1);
}
}
}
//通过角标位置换元素方法
public static void swap(int[] arr , int a , int b)
{
//定义一个int类型变量,接收arr数组a角标位上的元素
int i = arr[a];

//将b角标位上元素赋给a角标位
arr[a] = arr[b];

//将i变量接受的数,赋给b角标位
arr[b] = i;
}
//定义输出数组中元素方法,输出结果更加高级!
public static void printArray(int[] arr)
{
System.out.print("[");
//遍历数组
for(int x=0;x<arr.length;x++)
{
//如果x不是数组角标的最后一位
if(x!=arr.length-1)
//按这个语句输出,后面带 ,
System.out.print(arr[x]+", ");
//如果是数组的最后一位
else
//就按这个语句输出,后面带中括号
System.out.println(arr[x]+"]");
}
}
}


运行结果



数组中元素的查找

普通查找我就不说了,就是遍历数组,获取数组中元素去和要查找的元素进行是否相等的判断,如果相等就是找到了

但是普通查找效率太低,因为一般数组没有规律,我要找的数可能在最后一个,那就好从第一个开始一个一个找。所以我们使用折半查找。

折半查找可以提高效率,但是必须要保证数组是有序数组。

折半查找代码演示:

/*
折半查找代码演示

为了使代码看起来简便,我就直接定义一个有顺序的数组了,因为前面排序学过了嘛~
*/

class  ArrayDemo5
{
public static void main(String[] args)
{
//为了代码演示方便,定义一个有序数组
int[] arr = new int[]{1,3,5,7,9,11,20};

//调用折半查找方法一
//寻找arr数组中3的角标位
int max1 = halfSearch_1(arr,3);
//输出结果
System.out.println("3在数组中的角标位是:"+max1);

//调用折半查找方法二
//寻找arr数组中3的角标位
int max2 = halfSearch_2(arr,9);
//输出结果
System.out.println("9在数组中的角标位是:"+max2);
}
//折半查找的第一种方法
public static int halfSearch_1(int[] arr , int key)
{
//首先定义三个int类型变量
int min , max , mid;
//min是最小的角标位
min = 0;
//max是最大角标位
max = arr.length-1;
//mid是中间角标位
mid = (min+max)/2;

//创建循环,条件是key不等于中间角标位上的数
while(key!=arr[mid])
{
//判断,如果key大于arr[mid],说明key比中间值大,应该在右半部分查找
if(key>arr[mid])
//所以最小值要变成mid+1,
min = mid+1;
//否则如果key<arr[mid]那么就说明key比中间值小,应该在左边部分查找
else if(key<arr[mid])
//所以最大值变为了mid-1
max = mid-1;
//如果以上两种情况都不是,那么就是我们运气好,中间角标位上的数正好是我们要找的
else
return mid;

//判断,如果min>max了,说明没有找到元素,返回-1
if(min>max)
return -1;
//每次循环之后都有了新的max或min,所以要重新给mid赋值
mid = min+max/2;
}
//最后返回mid
return mid;
}

//折半查找的第二种方法
public static int halfSearch_2(int[] arr , int key)
{
//定义三个变量
int min = 0 , max = arr.length-1 , mid;
//定义循环,如果min<=max 就可以循环下去
while(min<=max)
{
//这句话的意思就是max+min的和的二进制位往右移了以为,相当于除以二
mid = (max+min)>>>1;
//判断key是否大于mid角标位上元素
if(key>arr[mid])
//如果是,则改变min的值
min = mid+1;
//判断key是否小于mid角标位上的元素
else if(key<arr[mid])
//如果是,则改变max的值
max = mid-1;
//否则返回mid,说明中间角标位上的数正好是我们要找的
else
return mid;
}
//否则就返回-1,说明没找到
return -1;
}
}


程序运行结果



利用数组进行进制转换

十进制---->二进制

/*
利用数组进行进制转换
十进制————>二进制
*/
class  ArrayDemo6
{
public static void main(String[] args)
{
//调用进制转换方法
toBin(12);
}
//十进制转二进制方法
public static void toBin(int num)
{
//定义二进制的表。
char[] chs = {'0','1'};

//定义一个数组作为临时容器
char[] arr = new char[32];

//定义一个操作数组的指针,为数组长度
int pos = arr.length;

System.out.print(num+"的二进制表示方式为:");

//定义循环,如果传入的数不为0则可以循环
while(num!=0)
{
//用num&1 得到的是num二进制数的最后一位,用一个变量接收
int temp = num & 1;
//从二进制表中获取最有一位二进制位对应的数,并反向存入数组容器中
arr[--pos] = chs[temp];
//将num向右移一位,让第二位变成最后一位,通过循环获取所有的二进制位。
num = num >>> 1;
}

//遍历容器数组
for(int x=pos; x<arr.length; x++)
{
//输出容器数组中的内容
System.out.print(arr[x]);
}
}
}


运行结果



二维数组

格式1:int[ ] [ ] arr = new int[3] [2];

定义名称为arr的二维数组,二维数组中有3个一维数组,

每一个一维数组中有2个元素,一维数组的名称分别为:

arr[0],arr[1],arr[2].

给第一个一位数组角标位赋值为78的写法是:

arr[0][1] = 78;

格式2:int[ ] [ ] arr = new int[3] [ ];

二维数组中有3个一维数组,每一个一维数组都是默认初始化之null

(因为数组是引用数据类型),可以对这个三维数组分别进行初始化:

arr[0]= new int[3]; arr[1] = new int[1]; arr[2] = new int[4];

格式3:int[ ] arr = { {1.2.3}.{6,5,80},{5,5,8,9}};

一维数组定义格式:int[ ]x; int x[ ];

二维数组定义格式:int [ ] [ ]y; int [] y [ ]; int y [ ] [ ];

谢谢大家的观看~!

-----------android培训java培训、java学习型技术博客、期待与您交流!---------
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: