StringBuffer类和数组的排序算法

2020.05.01课堂笔记

StringBuffer 类

  1. StringBuffer可以看作是一个字符容器,它的容量默认是16,但是可以根据具体情况,自动扩容。
  2. 我们在String类中要想拼接字符串,没拼接一次,就会创建一个新的空间,这样耗时又浪费空间。StringBuffer就解决了这个问题
  3. 构造方法
    • new StringBuffer():默认创建一个容量为16 字符串缓冲区对象。
      • 一般就创建默认容量的,因为当容量不够时,会自动扩容。
    • new StringBuffer(String str):创建一个指定字符串内容的字符串缓冲区对象
      • 也是String转换成StringBuffer的方法之一。
    • new StringBuffer(int capacity):创建一个指定容量的字符串缓冲区对象。
  4. 方法:
    • append():将任意类型的数据拼接到字符串尾部。
    • insert(int index,插入各种类型的数据):在指定位置处插入各种类型的数据,返回StringBuffer类型。
      • 插入字符串数组时,将字符串数组的地址值插入进去。
    • capacity():获取字符串缓冲区对象的容量。
    • length():获取对象的实际长度。
    • reverse():反转字符串
    • substring(int start);指定起始索引,截取一段字符串,返回string类型。
    • substring(int start,int end)指定起始索引和终止索引,截取一段字符串,返回string类型。
    • chartAt(int index);返回指定索引处的字符值。
    • indexOf(String str):在字符串缓冲池中查找指定字符串第一次出现的索引。
    • indexOf(String str,int fromIndex):在字符串缓冲池中,从指定索引处查找字符串第一次出现的索引。
    • lastIndexOf(String str):在字符串缓冲池中反向查找指定字符串第一次出现的索引。
    • delete(int start, int end ):删除指定起始索引和终止索引范围的字符串。返回StringBuffer类型
    • deleteCharAt(int index):删除指定索引处的字符。
示例:
public class Test6 {
    public static void main(String[] args) {
        StringBuffer s = new StringBuffer("abc");
//        capacity()输出字符串缓冲区的容量,默认容量是16.此处容量打印19。
//        是把默认容量和添加的字符串相加后的容量。
        System.out.println(s.capacity());
//        System.out.println(s.append(12).append(arr).append(3.14));
//        append()的使用,返回一个对象可以继续调方法。
        System.out.println(s.append(12).append(3.14));
        StringBuffer s1 = s.insert(1, "asdf");
        System.out.println(s1);
//        获取指定索引处的字符值
        char c = s1.charAt(3);
        System.out.println(c);
        StringBuffer s2 = s1.append(3.14);
//        替换指定索引处的内容,含头不含尾
        System.out.println(s2.replace(9, s2.length(), "*"));
        StringBuffer s3 = s.append("qwer");
//        反转功能
        StringBuffer reverse = s3.reverse();
        System.out.println(reverse);
        System.out.println("===========");
        StringBuffer sb=new StringBuffer("qaz");
        StringBuffer sb1 = sb.append("wsx");
        System.out.println(sb1);
        sb.append("edc");
        System.out.println(sb);
        System.out.println("========");
//        StringBuffer---->String 转换
        System.out.println(sb.toString());
        System.out.println(sb.substring(0, sb.length() - 1));
//        String------>StringBuffer
        String str="lkm";
        StringBuffer buffer = new StringBuffer(str);
        buffer.append("kkkkhjn");
        System.out.println(buffer);
//        delete();删除指定开始和结束的数据。含头不含尾
        buffer.delete(buffer.length()-1,buffer.length());
        System.out.println(buffer);
    }
}

StringBuffer和StringBulider的区别

  1. 这两个类的方法都相同,
  2. 区别:
    • StringBuffer是线程安全的,但是它的效率低。
    • StringBulider是线程不安全的,它的效率高。
      • 对于单线程的,两个方法没区别,StringBulider因为效率高会更好。

String和StringBuffer作为参数传递

public class Test7 {
    public static void main(String[] args) {
        String s1="abc";
        StringBuffer s2 = new StringBuffer("abc");
        getStr(s1);
        getStr(s2);
        System.out.println(s1); //abc
        System.out.println(s2);//abcqwe
    }

//    StringBuffer作为参数传递,是一个引用传递,把地址值传递过去,形参改变影响实参
    private static void getStr(StringBuffer s2) {
        s2.append("qwe");
    }

//    String 作为参数传递,是当作一个数值传递,形参改变不影响实参。
    private static void getStr(String s1) {
        s1+="qwe";
    }
}

数组的高级操作

  1. 冒泡排序:数组中的元素两两比较,大的往后放,一轮比较结束,最大的就在最后,然后在依次比较。
//冒泡法排序数组数值,每次将两个数据对比,将大的数放在后面,以此一轮对比结束,最大的
//数据就在最后。然后在对比一次,不用对比最后那个数据。这样就会将所有的数据按顺序排列。

public class Test {
    public static void main(String[] args) {
        int[] arr = new int[]{12, 13, 24, 56, 3, 19, 51, 8};
        for (int j = 0; j < arr.length - 1; j++) {
            for (int i = 0; i < arr.length - 1 - j; i++) {

//                arr[i]>arr[i+1],是将数据从小到大排列
//                arr[i]<arr[i+1],是将数据从大到小排列。
                if (arr[i] > arr[i + 1]) {
                    int m = arr[i];
                    arr[i] = arr[i + 1];
                    arr[i + 1] = m;
                }
            }
        }
        for (int k = 0; k < arr.length; k++) {
            System.out.print(arr[k] + " ");
        }
    }
}
  1. 选择排序法

  2. /*
    选择排序方法,对数组排序,从0索引处开始和后面的每个数据比较,将小的放到最前面
    这样每轮结束之后,最小的数就在最前面。
    然后从1 索引处开始,依次比较,结束之后就把数据从小到大排序了。
    */
    
    import java.util.Arrays;
    
    public class Test2 {
        public static void main(String[] args) {
            int[] arr = new int[]{12, 13, 24, -7, 3, 19, 5, 8};
            for (int index = 0; index < arr.length-1; index++) {
                for (int i = index+1; i < arr.length; i++) {
                    if (arr[index]>arr[i]){
                        int m=arr[index];
                        arr[index]=arr[i];
                        arr[i]=m;
                    }
                }
            }
    //        数组遍历的方法
            System.out.println(Arrays.toString(arr));
        }
    }
    
  3. 直接插入排序法

    //直接插入法排序数组
    //依次从头开始将数据插入到有序数组中,并仍然保持有序。
    
    import java.util.Arrays;
    
    public class Test3 {
        public static void main(String[] args) {
            int[] arr = {1, 23, 21, 5, 3, -1, 80, -34};
    //        刚开始将第一个数据看成是有序数列,和第一个对比排序
            for (int index = 1; index < arr.length; index++) {
    //            每次对比不止和前一个数对比,要和前面所有的数据对比,才能确定最终位置。
                for (int j = index; j > 0; j--) {
                    if (arr[j] < arr[j - 1]) {
                        int m = arr[j];
                        arr[j] = arr[j - 1];
                        arr[j - 1] = m;
                    }
                }
            }
            System.out.println(Arrays.toString(arr));
            System.out.println("==========");
    
    //        第二个方法
            for (int i = 1; i < arr.length; i++) {
                int j=i;
                while (j>0&&arr[i]<arr[i-1]){
                    int mi=arr[i];
                    arr[i]=arr[i-1];
                    arr[i-1]=mi;
                    j--;
                }
            }
            System.out.println(Arrays.toString(arr));
        }
    }
    
  4. 快速排序法

    //快速排序法(挖坑排序法)
    /*
    思想:是把第一个数值挖出来(坑位1),然后从后向前找,直到找到比它小的,然后放在(坑位1),
    腾出(坑位2)
    然后从前向后找,直到找到比它大的挖出来,放到(坑位2),腾出(坑位3),
    每次从后向前或者从前向后找,都要从上次索引的位置后出发,不要从头开始找。
    直到索引相同了就结束了,这样就分出左右区,然后在左右区中,左区肯定比起始数据都小,
    右区肯定比起始数据都大,然后在左右区继续这样排序,就会得到有序数列。
    */
    
    import java.util.Arrays;
    
    public class Test4 {
        public static void main(String[] args) {
            int[] arr = {12, 4, 23, 1, 4, 35, 67, 2};
            Tools tools = new Tools();
            tools.quicksore(arr, 0, arr.length - 1);
            System.out.println(Arrays.toString(arr));
        }
    }
    
    class Tools {
        public void quicksore(int[] arr, int start, int end) {
            if (start < end) {
                int i = getIndex(arr, start, end);
    //            返回分界线,分解线的前一个索引就是左区的终止索引
                quicksore(arr, start, i - 1);
    //             返回分界线,分解线的后一个索引就是右区的开始索引
                quicksore(arr, i + 1, end);
            }
        }
        public int getIndex(int[] arr, int start, int end) {
            int s = start;
            int e = end;
    //        起始比较数据
            int x = arr[start];
            int index = -1;
            while (s < e) {
    //            从后向前找,直到找到比它小的,
                while (s < e && arr[e] > x) {
                    e--;
                }
    //            将数据放到坑中,自己的位置腾出来
                if (s < e) {
                    arr[s] = arr[e];
    //                让从前向后找的所以增加一个位置
                    s++;
                }
    //            从前向后找,直到找到比它大的数据
                while (s < e && arr[s] < x) {
                    s++;
                }
    //            将数据放到坑中,自己的位置腾出来
                if (s < e) {
                    arr[e] = arr[s];
    //                让从后向前找的索引向前进一个位置
                    e--;
                }
            }
    //        索引相遇了,将起始数据放到相遇的坑位,
            arr[s] = x;
    //        相遇点就是分界线
            index = s;
            return index;
        }
    }
    

二分法查找元素:

  • 二分法查找元素的前提是,这个数组是有序数列,如果要查找的元素在后面,此方法的效率高
//二分法寻找一个数据的索引,这样寻找速度比较快,比遍历的效率高。
//二分法的前提是:这个数组必须是有序的。
/*思路:就是每次寻找中间的数据,和目标对比。
 * 如果相等直接输出索引
 * 大于中间值,那就在后面的范围以此方法寻找
 * 小于中间值,那就在前面的范围以此方法寻找
 * */

public class Test5 {
    public static void main(String[] args) {
        int[] arr = {10, 20, 30, 40, 50, 60, 90, 100, 110};
        Demo demo = new Demo();
        int i = demo.getIndex(arr, 40, 0, 5);
        System.out.println(i);
    }
}

class Demo {
    public int getIndex(int[] arr, int a, int start, int end) {
        int m = 0;
        int s = start;
        int e = end;
        while (s <= e) {
            m = (s + e) / 2;
//        中间值等于目标值,返回中间值的索引
            if (arr[m] == a) {
                return m;
            }
//        如果中间值小于目标值,那就将中间值的索引的下一个索引作为起始索引,在新的
//            在新的一半区域中寻找。
            if (arr[m] < a) {
                s = m + 1;
            }
            if (arr[m] > a) {
                e = m - 1;
            }
        }
        return m;
    }
}

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值