15.字符串String
15.1.String的基本特征
String 的父类是Object
String 的类是final类,不能被继承
String 的底层是由final char[] 组成的,是一个常量不可变化
String 是不可变是指当前的字符串不能发生任何变化,如果对当前字符串作出了任何的操作都会产生一个新的字符串对象
String 效率会很低
String aa = “我们”+”都是”+”山西农大”+”好”+”学生”;
String sqlStr=”insert into book vlaues(“+bid+”,”+bname+”,”+bprice+”,”+bnumber+”)”;
每一次的字符串连接都会产生新的对象,在整个连接字符串的过程中会产生大量的中间对象然后在销毁这些中间对象。
15.2.字符串的常用方法
15.2.1.判断字符串是否相同
在字符串中如果使用equals判断,任何两个字符串只要内容相同都返回true;
如果使用==判断相等 ,连个字符串直接付值会返回true;
String str1 = “你好”;
String str2 = “你好”;
String str3 = str2;
则 str1 == str2 == str3 都是true
String str4 = new String(“你好”);
Str4 不等于(==)(str1,str2,str3)中的任何一个
String name3 =”你好”;
String name1 = “你好”; //name1 和name3 共创建了一个对象
String name2 = new String(“你好”); //创建了两个对象
//String 是不可变是指当前的字符串不能发生任何变化,如果对当前字符串作出了任何的操作都会产生一个新的字符串对象
// str1 = str1 + ",天安门上太阳升";
// str1 = str1 +",太阳升起好看毛主席";
// System.out.println(str1);
//判断字符串是否相同 equals 和 ==
System.out.println("str1.equals(str2):"+str1.equals(str2));
System.out.println("str1 等于 str2:"+(str1 == str2));
System.out.println("str1.equals(str3):"+str1.equals(str3));
System.out.println("str1 等于str3:"+(str1 == str3));
System.out.println("str1.equals(str4):"+str1.equals(str4));
System.out.println("str1等于 str4"+(str1== str4));
System.out.println("str2等于 str4"+(str2== str4));
15.2.2.等值判断忽略大小写equalsIgnoreCase
String str1 ="Hello";
String str2 = "hello";
System.out.println("str1.equals(str2):" + str1.equals(str2)); //false
System.out.println("str1.equalsIgnoreCase(str2):" + str1.equalsIgnoreCase(str2)); //true
15.2.3.获取字符串指定位置的字符(chatAt(index))
String str1 = "我爱祖国天安门";
char zi = str1.charAt(1);
System.out.println("zi:" + zi);
Scanner input = new Scanner(System.in);
boolean isRight =true;
do{
isRight =true;
System.out.println("请输入一个字符串(只能包括数字字母下划线):");
String info = input.next();
//判断字符串中是否存在非法字符
for(int i = 0;i<info.length();i++){
char zifu = info.charAt(i);
if(!(zifu=='_' || zifu>='0'&&zifu<='9' || zifu>='a'&&zifu<='z' || zifu>='A'&&zifu<='Z')){
isRight = false;
break;
}
}
if(isRight == false)
System.out.println("存在非法字符");
}while(isRight == false);
15.2.4.Length() 方法
用于获取字符串的长度
数组中 length是属性,字符串中length是方法
String info =”我爱祖国天安门”;
Int lenght = info.length();
15.2.5.Split()把字符串按着指定的字符分割成一个数组
//通过分割字符串获取文件的名称和文件的类型
//利用原有的文件名和一定的规则(年月日信息)形成新的文件名
SimpleDateFormat sdf = new SimpleDateFormat("yyyyMMddhhmmssms");
Date date =new Date();
String file = "tlbb.jpg";
String[] files = file.split("\\."); //数组的第一个元素就是文件名数组的第二个元素就是文件类型
file = files[0]+"_"+sdf.format(date)+"."+files[1];
System.out.println("新的文件名:" + file);
15.2.6.Trim()取出字符串两侧的空格
//trim()取出左右两侧空格
String info = " 我爱祖国天安门 ";
info = info.trim() + ",天安门上太阳升";
System.out.println(info);
15.2.7.indexOf() lastIndexOf() 用于查找子字符串的位置,找不到返回-1
//indexOf() lastIndexOf查找子字符串所在的位置
String info4 ="我们爱祖国,祖国在我们的心中,我们就是祖国的未来";
int index = info4.indexOf("祖国");
System.out.println("index:" + index); //3
int index2 =info4.indexOf("祖国", 4);//查找字符串,从指定的位置之后
System.out.println("index2:"+index2 ); //6
int index3 = info4.indexOf("美国");
System.out.println("index3:" + index3); //找不到返回-1
int index4 = info4.lastIndexOf("祖国"); //查找最后一次出现的位置返回19
System.out.println("index4:"+index4);
int count= 0;
int index5 =-1;
//通过循环查询"祖国"出现所有位置和次数
do{
index5 =info4.indexOf("祖国",index5+1);
if(index5!=-1){
count++;
System.out.println("第"+count+"次的位置:"+ index5);
}
}while(index5!=-1); //如果存在继续循环查找
System.out.println("一共出现了:"+count+"次");
15.2.8.简单案例(使用string字符串的方法验证邮箱格式)
邮箱格式的要求是…@…com.cn
//1输入邮箱的信息
Scanner input = new Scanner(System.in);
System.out.println("请输入邮箱");
String email = input.next();
//2去除邮箱的空格
email = email.trim();
//3验证邮箱是否存在@ 和 . (indexOf)
int index1 = email.indexOf("@");
int index2 = email.lastIndexOf(".");
if(index1== -1 || index2 == -1){
System.out.println("邮箱必须包括@和.");
return ;
}
//4验证@是否出现了多次
int lastIndex = email.lastIndexOf("@");
if(index1 !=lastIndex){
System.out.println("邮箱中@出现了多次");
return;
}
//5验证@和.的位置
if(index2<index1){
System.out.println("@的位置必须在最后一个.的前面");
}
//大法师@qq.com
//6分别获取邮箱的名称,类型,域名
String emailname = email.substring(0, index1); //从头截取到@前面
String emailtype = email.substring(index1+1,index2); //从@的后一个截取到.的前一位
String emialyu = email.substring(index2+1); //从最后一个.开始截取到最后
//7判断是否包含非法字符
boolean nameRight = checkChar(emailname);
boolean typeRight = checkChar(emailtype);
if(nameRight== false || typeRight== false){
System.out.println("邮箱中只能包括数字字母下划线");
return;
}
//8域名只能是 com 或 cn 忽略大小写
if(!("com".equalsIgnoreCase(emialyu)|| "cn".equalsIgnoreCase(emialyu))){
System.out.println("定义域名只能是com cn");
return;
}
System.out.println("邮箱格式正确");
//9判断字符串中是否包含特殊字符(方法)
public static boolean checkChar(String str){
boolean isRight =true;
//判断字符串中是否存在非法字符
for(int i = 0;i<str.length();i++){
char zifu = str.charAt(i);
if(!(zifu=='_' || zifu>='0'&&zifu<='9' || zifu>='a'&&zifu<='z' || zifu>='A'&&zifu<='Z')){
isRight = false;
break;
}
}
return isRight;
}
15.2.9.Replace() 替换单个字符,ReplaceAll() 替换所有的字符串
// //字符串的替换
// String info1 = "中国人民是不会犯罪的,犯罪分子无处可逃";
// String info2 = info1.replace('犯', '饭');
// System.out.println(info2);
// String info3 =info1.replaceAll("犯罪", "**");
// System.out.println("info2:" + info2);
// System.out.println("info3:" + info3);
15.2.10.concat() 字符串的连接
// //字符串的连接
// String info = "我爱祖国天安门"+",天安门上太阳升";
// String info4 =info.concat(",太阳升起亮堂堂");
// System.out.println("info4:" + info4);
15.2.11.toUpperCase() toLowerCase()字符串大小写转换
// String info5 = "Hello";
// String info6 =info5.toUpperCase();
// String info7 = info5.toLowerCase();
// System.out.println("大写后的内容:" + info6);
// System.out.println("小写后的内容:" + info7);
15.3.总结字符串的必须记住的方法
length() 获取字符串的长度
equals() 判断字符串是否相等
equalsIgnoreCase() 判断字符串是否相等(忽略大小写)
indexOf() 判读字符串的位置 ,返回-1表示没有
lastIndexOf() 判断最后一个字符串出现的位置
subString() 截取子字符串
Split()分割字符串
charAt() 获取指定位置的单个字符
replace() 替换字符串中的某一个字符
replaceAll() 替换字符串中的某一个字符串
15.4.StringBuilder 和StringBuffer
StringBuilder 和StringBuffer提供了一些对String 的内容的操作方法
StringBuffer strBuffer = new StringBuffer();
strBuffer.append("我爱"); //追加字符串
strBuffer.append("北京");
strBuffer.append("天安门");
strBuffer.delete(2, 4);//删除字符串
strBuffer.insert(3, "呵呵"); //插入字符串
StringBuilder strBuilder =new StringBuilder();
strBuilder.append("我爱");
strBuilder.append("北京");
strBuilder.append("天安门");
strBuilder.delete(2, 4);
strBuilder.insert(3, "呵呵");
System.out.println(strBuffer.toString());
System.out.println(strBuilder.toString());
15.5.StringBuilder 和StringBuffer,String 之间的关联
//String因为字符串是常量,不能修改内容。在内容变化的时候会创建多个对象在内存中不断的分配空间,不断垃圾回收,效率低
//StringBuffer,StringBuilder都是string的增强了,可以在原有的字符串上面做多次的变化,而创建的对象只有一个效率要比string高很多。
其中StringBuffer是一个线程安全类,在使用的时候会做线程同步,效率比StringBuilder要低一些
StringBuilder是一个线程不安全的类,不会涉及线程同步问题,所以效率要高一些。
StringBuilder在三个类中使用的最多一些。
16.集合
16.1.集合的三大接口:list,set,map
List 可以重复,有顺序。 set 不重复 ,没有顺序,Map 健值对 健不能重复
16.2.List 的实现了ArrayList
默认集合的操作对象是Object 类型,可以保存任何类型的对象但在遍历的时候需要进行类型判断,比较麻烦,一般我们在使用的时候是泛型集合
泛型集合: 在集合定义的时候,通知集合允许保存的数据类型。
当使用的是集合的时候就只能保存同一个数据类型,在获取集合对象的时候也不需要进行类型判断
List 集合名称 = new ArrayList();
16.3.List的常用方法
Add() 在集合的最后添加对象
Add(index,obj) ; 在指定的位置插入对象
Addall() 在一个集合中添加另一个集合的内容
Size()获取集合的元素个数
isEmpty() 判断集合中是否存在内容
Remove() 删除单个对象,删除对象的原则是判断是否是同一个对象而对象的值是否相同
Contains() 判断集合中是否包含某一个对象
集合的遍历
Iterator()迭代器可以遍历所有的集合类型(list,set,map)
for循环只能遍历list 的内容
案例
//创建一个学生的集合
List<Student> stuList = new ArrayList<Student>();
//添加对象
Student stu1 = new Student("张三","女");
Student stu2 = new Student("李四","男");
Student stu3 = new Student("王五","女");
Student stu4 = new Student("赵柳","男");
Student stu5 = new Student("李四","男");
Student stu6 = stu3;
stuList.add(stu1);
stuList.add(stu2);
stuList.add(stu3);
stuList.add(stu5); //stu5 和 stu2 不叫重复对象,只是属性值刚好相同
stuList.add(stu6); //添加重复的对象 stu6 == stu3
stuList.add(2, stu4); //在指定的位置插入对象
//查询集合中的元素个数 如果size ==0表示集合中没有内容
int size =stuList.size();
System.out.println("集合中的元素个数:" + size);
//判断集合元素是否为空
boolean isEmpty =stuList.isEmpty();
System.out.println("是否为空:" + isEmpty);
//移除某一个元素
stuList.remove(stu6); //移除的是重复对象的第一个
stuList.remove(stu5);
//判断某一个对象是否存在
Student check_stu = new Student("张三","女");
boolean isHave =stuList.contains(check_stu);
System.out.println("isHave:"+ isHave); //false 同名同性别不一定是同对象
check_stu = stu1; //check_stu == stu2;两个对象是相同的
isHave = stuList.contains(check_stu);
System.out.println("isHave:"+ isHave); //true
//遍历:所有的集合类型都可以采用iterator的方式便利
Iterator<Student> stuIterator = stuList.iterator();
while(stuIterator.hasNext()){
Student temp_stu = stuIterator.next();
System.out.println(temp_stu);
}
//list 特别的遍历 利用for循环或foreach都可以
System.out.println("===================");
for(int i =0;i<stuList.size();i++){
Student stu = stuList.get(i);
System.out.println(stu);
}
16.4.List的三个实现类的区别和联系
LinkedList 底层是由链表实现,在增加删除元素的时候要快,但遍历要慢
因为LinkedList多实现了接口所有方法要比ArrayList要多
ArrayList 底层是数组实现默认容量是10 ,扩容1.5倍. 遍历要快,增加删除要慢
同时线程不安全,效率高
Vector 底层也是数组实现,默认容量10,扩容2被,遍历要快,增加删除要慢
同时线程安全,效率低
17.Set 集合
Set stuSet = new HashSet();
无序,不可重复
不可重复的判断规则是:首先调用对象的hashCode ,如果HashCode相同,则调用eqals方法
常用方法和List 相同的: 重点的方法: add ,remover ,container ,iterator遍历
Set 不支持for循环遍历只能用iterator遍历
HashSet 和TreeSet的区别和联系
HashSet与TreeSet接口的一点不同,HashSet 保存的数据是无序的,TreeSet保存的数据是有序的
利用TreeSet保存自定义类对象的时候,自定义所在的类一定要实现Comparable接口,否则无法排序
TreeSet 依靠的是Comparable 来区分重复数据;HashSet 依靠的是hashCode()、equals()来区分重复数据
里面都不允许保存重复数据。
18.Map集合
Map保存数据的方法以键值对的方式去保存,键不能重复,值可以重复
Map的常用方法
Put() 在集合中保存数据
Get() 根据KEY获取VALUE的信息
KeySet() 获取所有的KEY
VALUES() 获取所有的value
isEmpty 判断集合的的元素是否为空
Size() 获取Map的元素个数
//key 名字 value 家庭住址
Map<String,String> strMap = new HashMap<String,String>();
strMap.put("张三", "河北省石家庄兴华大街100号");
strMap.put("李四", "河北省唐山市兴华大街110号");
//查看一共有多少个学生信息 size()
int stusize = strMap.size();
System.out.println("一共有:"+stusize+"学生的信息");
//查询某一个学生的家庭住址containKey get
String findname = "王五";
if(strMap.containsKey(findname))
{
String address = strMap.get(findname);
System.out.println(findname +"家庭住址:"+ address);
}else{
System.out.println("没有找到"+findname+"的信息");
}
//修改王五的家庭住址
System.out.println("替换学生的信息:");
String newname ="王五";
String newaddress="河南省驻马店市政府街100号";
//strMap.put(newname, newaddress);
strMap.replace(newname, newaddress);
//把李四的信息移除
String removename = "李四";
if(strMap.containsKey(removename)){
strMap.remove(removename);
System.out.println(removename +"移除成功");
}else{
System.out.println(removename +"不存在,不能移除");
}
//显示所有的学生的地址
Iterator<String> nameIter= strMap.keySet().iterator();
System.out.println("姓名\t地址");
while(nameIter.hasNext()){
String name = nameIter.next();
String address = strMap.get(name);
System.out.println(name+"\t"+address);
}
//情况所有的元素
strMap.clear();
System.out.println("还有没有学生信息 :"+ strMap.isEmpty());
System.out.println("Map结束");
遍历map的方法有三种<循环key,循环values,循环map对象>
//第一种:遍历可以 keyset()
Set<String> keySet = stuMap.keySet();
Iterator<String> keyIter = keySet.iterator();
while(keyIter.hasNext()){
String key = keyIter.next();
//通过key获取map中的value
Student stu = stuMap.get(key);
System.out.println(key +" " + stu);
}
//第二种:遍历vlaues
System.out.println("所有的VALUES");
Collection<Student> stuColl = stuMap.values();
Iterator<Student> stuIter = stuColl.iterator();
while(stuIter.hasNext()){
Student stu = stuIter.next();
System.out.println(stu);
}
//第三种: 遍历KEY-VALUE对象
System.out.println("所有的entry (key+ value)");
Set<Entry<String,Student>> entrySet = stuMap.entrySet();
Iterator<Entry<String,Student>> entryIter = entrySet.iterator();
while(entryIter.hasNext()){
Entry<String,Student> entry = entryIter.next();
String key = entry.getKey();
Student student = entry.getValue();
System.out.println(key+" "+ student);
}
19.Map的实现类的区别
HashMap
根据键的hashCode值存储数据,只允许一条记录的键为null,速度快,线程不安全
Hashtable
常用功能与HashMap类似,速度慢,线程安全
LinkedHashMap
是HashMap的一个子类,保存了记录的插入顺序
TreeMap
是SortedMap接口的实现,key有序以”二叉树"的格式存储
20.Collection 和Collections 的区别
Collection是一个接口,是List和Set的父接口,它里面保存的数据的特点是:无序,且重复
Collections是一个工具类,不能实例化,提供了一些静态的方法,用于是实现对于集合的一些常用功能。
集合中保存的都是对象的引用
Proerties ,Queue,Stack