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

黑马程序员--java基础复习之数组

2015-03-16 22:12 363 查看
<span style="font-family: Arial, Helvetica, sans-serif; background-color: rgb(255, 255, 255);">------<a href="http://www.itheima.com" target="blank">Java培训、Android培训、iOS培训、.Net培训</a>、期待与您交流! -------</span>


在刚开始学习数据类型的时候,我们就学习过了八种基本数据类型 byte short int lang float double char boolean ,还有就是三种引用类型,第一个就是数组,以及类和接口。

首先,是数组的定义,数组是同一类型数据的集合。其实就是一个容器,就是用于存储数据的地方。数组的好处就是可以自动给数组中的元素从0开始编号,这样方便于操作元素。如同每个班里的学生都有一个学号一样,方便管理学生。

然后是数组的定义格式。

第一种:元素类型[] 数组名 = new 元素类型[元素个数或数组长度];

例如:

int[]  arr=new int[3];


这表示的是定义了一个数据类型为int,长度为3的数组,它的元素角标是从0开始的,最后一个角标为2。

第二种:元素类型[] 数组名 = new 元素类型[]{元素1,元素2,....};

例如:

int[] arr=new arr[]{5,4,16};
int[]  arr1={7,5,9};
上面两行代码都表示定义了一个长度为3的int类型的数组,并且都初始化了值

数组在内存中的表现形式

int []  x=new int[3];


上面这句代码在内存中是这样的,如图:






和局部变量不一样,引用型变量x是存放在栈内存中的,而数组是先分配一个地址值,然后在堆内存中开辟出一片空间,这时数组中的元素就已经有了默认初始化值。int类型默认初始化值为0,boolean 类型为false,String 类型为null.然后将这个地址值赋值给变量x,即x指向了堆内存中的这个数组。当给数组中的第一个元素x[0]赋值为59时,在堆内存中数组的第一个元素的值就修改为59,如上图。当我们将null
赋值给引用型变量x时,即 x=null时,栈内存中x的值就变成了null,就不再指向数组在堆内存的地址,那么,堆内存中的这个数组就变成没用的了,因为没有变量再指向它了,那么java就会调用垃圾回收机制来回收它了。

那么下面说栈内存和堆内存的作用和区别

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

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

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

C、实体中的变量都有默认初始化值。

D、实体不再被使用,会在不确定的时间内被垃圾回收器回收。

小细节:1、以下这两种定义数组的方式都可以,效果是一样的,推荐使用第一种

int[] arr=new int[2];
int arr1[] =new int[2];


2、静态初始化数组时,不要写长度,如下

int[]   arr=new int[3]{1,8,6};



操作时常见问题

1、角标越界异常(ArrayIndexOutOfBoundsException ),如下图






其中,ArrayIndexOutOfBoundsException ,这个就是数组角标越界异常,这是因为操作数组时,访问到了数组中不存在的角标。如代码中所示,长度为3的数组,最大的角标位为2,而不是3。

2、空指针异常(NullPointerException) ,如图






当将null的值赋给arr时,arr的地址值就不再指向数组在堆内存中的位置了,所以用arr来操作数组中的元素时就会出现这个异常。NullPointerException:空指针异常,当引用没有任何指向值为null的情况,该引用还在用于操作实体。

数组的常见操作

1、数组的遍历

class ArrayDemo
{
public static void main(String[] args)
{
//数组的遍历操作:获取数组中的元素
//定义一个长度为3的数组
int[] arr=new int[3];
for(int x=0;x<3;x++)
{
System.out.println("arr["+x+"]="+arr[x]);
}
}
}


定义了一个长度为3的数组,但是并没有给其中的元素赋值,结果:


可以看出,int类型数组默认初始化值为0。

数组有一个属性length,可以获取数组的长度

class ArrayDemo
{
public static void main(String[] args)
{
//数组的遍历操作:获取数组中的元素
//length:获取数组中元素的个数,使用方式:数组名.length
//定义一个长度为3的数组
int[] arr=new int[]{3,5,7,13,6,88};
for(int x=0;x<arr.length;x++)
{
System.out.println("arr["+x+"]="+arr[x]);
}
}
}


结果:


下例

<span style="font-size:12px;">class ArrayDemo
{
public static void main(String[] args)
{
//数组的遍历操作:获取数组中的元素
int[] arr=new int[]{3,5,7,13,6,88};
printArray(arr);
}

//功能:打印数组中的元素,元素间用逗号隔开
static void printArray(int[] arr)
{
System.out.print("[");
for(int x=0;x<arr.length;x++)
{
if(x!=arr.length-1) //当前元素不是最后一个元素时
System.out.print(arr[x]+",");
else
System.out.println(arr[x]+"]"); //当遍历到最后一个元素时,不加逗号
}
}
}</span>
结果:


2、获取数组中的最值(最大值、最小值)

<span style="font-size:12px;">/*
获取数组中的最值

给定一个数组{6,8,4,1,14,25}

*/

class ArrayTest2
{
public static void main(String[] args)
{
int[] arr=new int[]{6,8,4,1,14,25};
int max=getMax(arr);
System.out.println(max);
}

/*
需求:获取数组中的最大值,以及最小值
获取数组中的最大值
思路:1、获取最大值需要进行比较,每一次比较都会有一个较大的值。因为该值不
不确定,所以定义一个变量用来存储这个较大值。
2、通过遍历,让数组中的元素分别和这个变量的值进行比较,若值大于该变量的值,则
该变量存储这个较大的值。
3、循环完成后,所有的元素都比较完成,那么该变量存储的就是数组中的最大值了。
*/
public static int getMax(int[] arr)
{
int max=arr[0];
//从角标1的位置开始,因为max初始化值为arr[0],所以max不用和arr[0]比较。
for(int x=1;x<arr.length;x++)
{
if(max<arr[x])  //若数组中的元素值大于max的当前值,则将此元素的值赋给max
max=arr[x];
}
return max;
}
}</span>


结果:


3、选择排序

原理:将数组中第一个元素同其他元素比较大小,得到最小值并放成0标上.然后继续在剩下的元素中寻找第二个最小元素,放在第二个位置。依此类推。就能得到排序结果。

代码如下

<span style="color:#666666;">class ArraySortDemo
{
public static void main(String[] args)
{
int[] arr=new int[]{5,6,4,15,25,1,8,95};

printArray(arr);  //排序前
ArraySelectSort(arr);  //打印数组
printArray(arr); //排序后

}

/*
选择排序
*/
static void ArraySelectSort(int[] arr)
{
//外循环遍历数组
for(int x=0;x<arr.length-1;x++)
{
//内循环比较大小
for(int y=x+1;y<arr.length;y++)
{
//定义一个第三方变量,便于元素交换位置
int temp;
//若前一个元素比后一个元素大,则两元素互换位置
if(arr[x]>arr[y])
{
temp=arr[x];
arr[x]=arr[y];
arr[y]=temp;
}

}
}
}
//打印数组
static void printArray(int[] arr)
{
if(arr!=null)
{
System.out.print("[");
//遍历数组
for(int x=0;x<arr.length;x++)
{
if(x!=arr.length-1)
System.out.print(arr[x]+",");
else
System.out.print(arr[x]);
}
System.out.println("]");
}
}

}</span>
输出结果:



4、冒泡排序

原理: 1、先从头角标相邻两个元素之间进行比较,取较大值存放在后一个元素中,然后再与后一个元素的进行比较,直至最大值存放到最后一个元素中。

2、再重复1操作,每次计较次数减一,一圈比完后存放的较大元素不再参与比较。

代码如下:

class ArraySortDemo
{
public static void main(String[] args)
{
int[] arr=new int[]{5,6,4,15,25,1,8,95};

printArray(arr);  //排序前
ArrayBubbleSort(arr);  //打印数组
printArray(arr); //排序后

}
//对数组冒泡排序
//从角标0开始,相邻两个元素进行比较,符合条件就互换位置,每轮下来,最值出现在数组最后一个位置上。
//依此类推,每轮要比较的个数少一个。
static void ArrayBubbleSort(int[] arr)
{
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])
{
int temp;
temp=arr[y];
arr[y]=arr[y+1];
arr[y+1]=temp;
}
}
}
}

//打印数组
static void printArray(int[] arr)
{
if(arr!=null)
{
System.out.print("[");
//遍历数组
for(int x=0;x<arr.length;x++)
{
if(x!=arr.length-1)
System.out.print(arr[x]+",");
else
System.out.print(arr[x]);
}
System.out.println("]");
}
}

}


结果:


5、折半查找(两种折半方式,及一个整数返回插入有序数组后的位置)

class ArrayTest
{
public static void main(String[] args)
{
int[] arr={5,6,1,4,8,7,14,23};
int[] arr1={2,4,6,7,9,10,15,25,725};
//int index=getIndex(arr,14);
//折半查找一
int index=halfSearch(arr,22);
//折半查找二
int index1=halfSearch_1(arr,22);
//向有序数组中插入一数,得到该数的角标位置
int index2=halfSearch_2(arr1,22);
System.out.println(index+":"+index1+":"+index2);
}

/*
折半查找:提高效率,但是必须保证该数组是有序的数组。
第一种
*/
static int halfSearch(int[] arr,int key)
{
int min,mid,max;
min=0;
max=arr.length-1;
mid=(min+max)/2;

while(arr[mid]!=key)
{
if(arr[mid]>key)
{
max=mid-1;
}
else
{
min=mid+1;
}
mid=(min+max)/2;
if(min>max)
return -1;
}
return mid;
}

/*
折半查找
第二种方式
*/
public static int halfSearch_1(int[] arr,int key)
{
int min=0,max=arr.length-1,mid;
while(arr[min]<=arr[max])
{
mid=(min+max)>>1; //等同于除以2
if(arr[mid]>key)
max=mid-1;
else if(arr[mid]<key)
min=mid+1;
else
return mid;
}
return -1;
}

/*
向一个有序的数组中插入一个数,插入后该数组依然是有序的
原理:折半查找后,返回-1改成返回min的值,即是此数插入后的角标位置
两种方式的结果一样
*/
public static int halfSearch_2(int[] arr,int key)
{
int min=0,max=arr.length-1,mid;
while(arr[min]<=arr[max])
{
mid=(min+max)>>1; //等同于除以2
if(arr[mid]>key)
max=mid-1;
else if(arr[mid]<key)
min=mid+1;
else
return mid;
}
return min;
}

//从数组中查找某元素
//参数:int类型数组,int类型元素
static int getIndex(int[] arr,int key)
{
if(arr!=null)
{
for(int x=0;x<arr.length;x++)
{
if(arr[x]==key)
return x;
}
return -1;
}
return -1;
}

}


结果:


6、进制转换

代码如下:

class ArrayTest1
{
public static void main(String[] args)
{
toBin(6);
toHex(60);
toHexBySearch(60);
trans(60,15,4);
}

//十进制---->二进制
static void toBin(int num)
{
//定义一个字符串缓存,用于存储转换结果
StringBuffer sb=new StringBuffer();

while(num>0)
{
sb.append(num%2);
num=num/2;
}
System.out.println(sb.reverse());
}

//十进制转十六进制
static void toHex(int num)
{
//定义一个字符串缓存,用于存储转换结果
StringBuffer sb=new StringBuffer();
for(int x=0;x<8;x++)
{
int temp=num&15;
if(temp>9)
sb.append((char)(temp-10+'A'));
else sb.append(temp);

num=num>>>4;
}
//使用字符串缓存的反转功能,输入结果的正确顺序
System.out.println(sb.reverse());
}

/*
查表法:将所有的元素临时存储起来。建立对应关系。
*/
static void toHexBySearch(int num)
{
char[] ch=new char[]{'0','1','2','3','4','5','6','7','8','9','A','B','C','D','E','F'};

char[] arr=new char[8];
int pos=arr.length;
while(num!=0)
{
int temp=num&15;
arr[--pos]=ch[temp];
num=num>>>4;
//System.out.println(arr[pos]);
}
for(int x=pos;x<arr.length;x++)
{
System.out.print(arr[x]+",");
}
System.out.println();
}

//进制转换
//参数:要转换的数据,与的基数,偏移位数
static void trans(int num,int base,int offset)
{
if(num==0)
{
System.out.println(0);
return;
}
//通用查表数组
char[] ch=new char[]{'0','1','2','3','4','5','6','7','8','9','A','B','C','D','E','F'};

//最大长度是二进制的32位
char[] arr=new char[32];

int pos=arr.length;
//通过循环,倒序的方式向数组中插入
while(num!=0)
{
int temp=num&base;
arr[--pos]=ch[temp];
num=num>>>offset;
}

//从数组中实际位置开始输出(即第一个不为0的位置)
for(int x=pos;x<arr.length;x++)
{
System.out.print(arr[x]);
}

}
}


二维数组

数组中的数组

形象比喻:以前的一维数组,就如同一个箱子,箱子里面有很多小格子,每一个小格子用于存放一个元素,箱子里格子的个数即是数组的长度。现在有一个大箱子,里面放的不是小格子,而是一个个里面有很多小格子的箱子。这个大箱子就是二维数组。而这个大箱子里小箱子的个数即为这个二维数组的长度

二维数组的定义格式

int[][] arr=new int[2][4];

这行代码的意思是定义一个名称为arr的二维数组,二维数组里有两个一维数组,每个一维数组的长度为4;

int[][] arr=new int[2][];

这句代表定义了一个名称为arr的二维数组,里面有两个一维数组,每个一维数数的初始化值为null

int[][] arr={{2,4},{4,5,6},{44,8,2}};

定义一个名为arr的二维数组,该数组长度为3,其中的元素分别为{2,4},{4,5,6},{44,8,2}三个一维数组。

如下图,为二维数组与一维数组之间的关系判断






------<a href="http://www.itheima.com" target="blank">Java培训、Android培训、iOS培训、.Net培训</a>、期待与您交流!
-------

内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: