排序--DS

news2024/10/9 5:46:46

在这里插入图片描述


1. 排序

所谓排序,就是使一串记录,按照其中的某个或某些关键字的大小,递增或递减的排列起来的操作。
#稳定性: 假定在待排序的记录序列中,存在多个具有相同的关键字的记录,若经过排序,这些记录的相对次序保持不变,即在原序列中,r[i]=r[j],且r[i]在r[j]之前,而在排序后的序列中,r[i]仍在r[j]之前,则称这种排序算法是稳定的;否则称为不稳定的。
在这里插入图片描述

我们默认以升序的形式来介绍下面的各个排序算法:

1.1 插入排序

把待排序的记录按其关键码值的大小逐个插入到一个已经排好序的有序序列中,直到所有的记录插入完为止,得到一个新的有序序列,这就是我们插入排序的思路。实际在玩扑克牌时,我们用到的就是插入排序的思想。
在这里插入图片描述

1.1.1 直接插入排序

当插入第i(i>=1)个元素时,前面的array[0],array[1],…,array[i-1]已经排好序,此时用array[i]的排序码与array[i-1],array[i-2],…的排序码顺序进行比较,找到插入位置即将array[i]插入,原来位置上的元素顺序后移。通过将第i个元素与前面已经有序的i-1个元素进行比较,插入合适的位置实现排序。

public void insertSort(int[] arr) {  
	//从第2个元素(1下标)开始进行插入排序,因为一个元素相当于有序
    for (int i = 1; i < arr.length; i++) {  
        int tmp = arr[i]; //保存第i个还未进入有序序列的元素 
        int j = i-1;//从第i-1个元素开始往前逐个比较  
        for (; j >= 0; j--) {  
            if(arr[j] > tmp) {  
                arr[j+1] = arr[j];  
            }else {  
                break;  
            }  
        }  
        //在有效下标处或不大于他的元素后放  
        arr[j+1] = tmp;  
    }  
}

直接插入排序特性总结:

  1. 对于越接近有序的元素集合,直接插入排序的时间效率越高
  2. 直接插入排序的时间复杂度:O(N^2)
  3. 稳定性:稳定
  4. 空间复杂度:O(1)

1.1.2 希尔排序

希尔排序法又称缩小增量法。希尔排序法的基本思想是:先选定一个整数gap,把待排序序列中所有记录分成多个组,所有距离相同的记录分在同一组内,并对每一组内的记录进行排序。然后,减小间隔gap,重复上述分组和排序的工作。当到达gap = 1时,所有记录在统一组内排好序。
在这里插入图片描述

public void shellSort(int[] arr) {  
    int gap = arr.length;  
    while(gap > 1) {  
        gap /= 2;//分组不断缩小,直到间距缩小为1  
        //分组很大时,数组元素小,相当于有序;时间复杂度O(N)  
        //分组很小时,元素很大,此时元素也接近有序;时间复杂度O(N)  
        for (int i = 0; i < arr.length-gap; i++) {  
            int tmp = arr[i+gap];  
            int j = i;  
            //间距为gap  
            for (; j >= 0 ; j-=gap) {  
                if(arr[j] > tmp) {  
                    arr[j+gap] = arr[j];  
                }else {  
                    break;  
                }  
            }  
            arr[j+gap] = tmp;  
        }  
    }  
}

希尔排序总结:

  1. 希尔排序是在直接插入排序上的优化
  2. 当gap > 1时都是预排序,目的是让数组更接近于有序。当gap == 1时,数组已经接近有序的了,这样就会很快。
  3. 希尔排序实际上将一组数据分为间隔为gap的多组数据,然后对多组数据进行交替排序:当gap>1时为预排序,当gap == 1时相当于直接插入排序
  4. 我们可以认为希尔排序的时间复杂度为:O(N*LogN)
  5. 空间复杂度:O(1)
  6. 稳定性:不稳定

1.2 选择排序

每一次从待排序的数据元素中选出最小(或最大)的一个元素,存放在序列的起始位置,直到全部待排序的数据元素排完 。

1.2.1 直接选择排序

直接选择排序是在集合中每一次遍历找到一个最小值,将它与为排序的元素中的第一位元素交换,使得交换后的元素有序,接着重复上述步骤,直到集合中剩余一个元素
在这里插入图片描述

我们可以在实现选择排序的时候优化一下,一次遍历中选出最大值和最小值,将他们与未排序元素的末端和首端进行交换:

public void selectSort(int[] arr) {  
    int left = 0;  
    int right = arr.length-1;  
    while(left < right) {  
        int maxIndex = left;  
        int minIndex = left;  
        for (int i = left+1; i <= right; i++) {  
            if(arr[maxIndex] < arr[i]) {  
                maxIndex = i;  
            }  
            if(arr[minIndex] > arr[i]) {  
                minIndex = i;  
            }  
        }  
        swap(arr,left,minIndex);  
        //判断maxIndex==left情况,最大值下标出被交换  
        if(left++ == maxIndex) {  
            maxIndex = minIndex;  
        }  
        swap(arr,right--,maxIndex);  
    }  
}

优化后的直接选择排序需要注意的是,当进行最大值和最小值的交换问题时,可能出现最小值交换后,最大值的位置发生改变,所以在进行最大值交换时应该判断下最大值原来位置是否在最小值位置处。

if(left++ == maxIndex) {  
    maxIndex = minIndex;  
}

直接选择排序总结:

  1. 时间复杂度:O(N^2)
  2. 空间复杂度:O(1)
  3. 稳定性:不稳定

1.2.2 堆排序

堆排序(Heapsort)是指利用堆这种数据结构所设计的一种排序算法,它是选择排序的一种。它是通过堆来进行选择数据。需要注意的是排升序要建大堆,排降序建小堆。
在这里插入图片描述

public void heapSort(int[] arr) {  
    //建堆:时间复杂度:O(N)  
    for (int i = (arr.length-1-1) / 2; i >= 0; i--) {  
        shilfDown(arr,i,arr.length);//向下调整  
    }  
    //将大根堆堆顶元素与尾元素交换,使得元素有序  
    //时间复杂度:O(N*LogN)  
    int len = arr.length;  
    while(len-1 != 0) {  
        swap(arr,0,--len);  
        shilfDown(arr,0,len);//交换后堆顶元素重新向下调整  
    }  
}

//向下调整算法
private void shilfDown(int[] arr, int root, int length) {  
    int child = root * 2 + 1;  
    while(child < length) {  
        //找孩子节点中大的  
        if(child+1 < length && arr[child] < arr[child+1]) {  
            child++;  
        }  
        if(arr[child] > arr[root]) {  
            swap(arr,child,root);  
            //交换后可能打乱下面的堆,接着向下调整  
            root = child;  
            child = 2 * root + 1;  
        }else {  
            break;  
        }  
    }  
}

堆排序的特性总结:

  1. 排升序要建大堆,排降序建小堆。
  2. 时间复杂度:O(N*LogN)
  3. 空间复杂度:O(1)
  4. 稳定性:不稳定

1.3 交换排序

所谓交换,就是根据序列中两个记录键值的比较结果来对换这两个记录在序列中的位置,交换排序的特点是:将键值较大的记录向序列的尾部移动,键值较小的记录向序列的前部移动。

1.3.1 冒泡排序

两两元素相比较,前一个比后一个大就交换,直到将最大的元素交换到末尾位置。一趟排序将一个最大的数沉入底部,像泡泡一样,所以叫冒泡排序
在这里插入图片描述

public void bubbleSort(int[] arr) {  
    for (int i = 0; i < arr.length-1;i++) {  
        boolean flg = false;  
        for (int j = 0; j < arr.length-1-i; j++) {  
            if(arr[j] > arr[j+1]) {  
                swap(arr,j,j+1);  
                flg = true;  
            }  
        }  
        if(!flg) {  
            break;//没有交换说明已经有序  
        }  
    }  
}

冒泡排序特性总结:

  1. 时间复杂度:O(N^2)
  2. 空间复杂度:O(1)
  3. 稳定性:稳定

1.3.2 快速排序

快速排序是Hoare于1962年提出的一种二叉树结构的交换排序方法,其基本思想为:任取待排序元素序列中的某元素作为基准值,按照该排序码将待排序集合分割成两子序列,左子序列中所有元素均小于基准值右子序列中所有元素均大于基准值,然后最左右子序列重复该过程,直到所有元素都排列在相应位置上为止
在这里插入图片描述

public void quickSort(int[] arr) {  
    //递归过程给定区间  
    _quickSort(arr,0,arr.length-1);  
  
}  
  
private void _quickSort(int[] arr,int left,int right) {  
    if(left >= right) {  
        return ;  
    }  
    //将基准排好序  
    int pivot = parttion1(arr,left,right);  
    //递归排序左右区间  
    _quickSort(arr,left,pivot-1);  
    _quickSort(arr,pivot+1,right);  
  
}

快速排序特性的总结:

  1. 时间复杂度:O(N*LogN)
  2. 空间复杂度:O(LogN)
  3. 稳定性:不稳定

对于区间按照基准值划分为左右两部分(将基准排好序,即左区间所有元素均小于基准值;右区间所有元素均大于基准)中常见的方法有:

  • 挖坑法
  • Hoare版
  • 前后指针法
1. 挖坑法

挖坑法思路:

  1. 选出基准值(最左边)保存在临时变量中,然后留下一个坑位。
  2. 右指针从上次位置开始往前寻找(第一次时从数组末尾向前寻找),直到遇到比基准值小的值,将该值放入到坑中,而右指针所指向位置形成新的坑。
  3. 然后将左指针从上次位置开始向后寻找(第一次从数组头开始向后寻找),直到遇到比基准大的值,将该值放入坑中,左指针指向位置称为新的坑。
  4. 重复上述2、3步骤,直到左右指针相遇。最后将基准值放入坑中。

在这里插入图片描述

//挖坑法
private int parttion1(int[] arr,int left,int right) {  
     int pivot = left;  
     int tmp = arr[left];  
     while(left < right) {  
         //从右往左找小:向从右往左找是为了确保左边<=基准,右边>=基准  
         while(left < right && arr[right] >= tmp) {  
             right--;  
         }  
         //找到小的后将左边的坑填上,右边形成新的坑  
         arr[pivot] = arr[right];  
         pivot = right;  
         //从左往右找大  
         while(left < right && arr[left] <= tmp) {  
             left++;  
         }  
         //找到大的后将右边的坑填上,左边形成新的坑  
         arr[pivot] = arr[left];  
         pivot = left;  
     }  
     //最后的位置就填上基准  
    arr[pivot] = tmp;  
     return pivot;  
}
2. Hoare版

Hoare版思路:

  1. 选定一个基准值(以临时变量的形式保存起来),并记录好基准值所在的下标,基准值最好选定最左边或者最右边
  2. 确定两个指针left 和right 分别从左边和右边向中间遍历数组。
  3. 这里以选最左边为基准值为例:

3.1 让right指针先往前走,如果遇到小于基准值的数就停下来
3.2 然后左边的指针left在向后走,遇到大于基准的数就停下来
3.3 交换left和right指针所指向位置的值。然后重复上述操作,直到left == right ,此时将基准值与left(right)位置的值交换。

在这里插入图片描述

//2. Hoare法  
private int parttion2(int[] arr,int left,int right) {  
    int tmp = arr[left];  
    int tmpIndex = left;  
    while(left < right) {  
        //从右往左找小  
        while(left < right && arr[right] >= tmp) {  
            right--;  
        }  
        //从左往右找大  
        while(left < right && arr[left] <= tmp) {  
            left++;  
        }  
        swap(arr,left,right);//将大的和小的所处的位置互换  
    }  
    //将相遇的位置和基准的位置换,形成左(不大于)右(不小于)  
    swap(arr,left,tmpIndex);  
    return left;  
}

需要注意的是,如果选取最左边的为基准,一定要先让right指针找小,否则可能出错。

3. 前后指针法

前后指针法思路:

  1. 选定基准值,定义prev和cur指针(cur = prev + 1)
  2. cur先走,遇到小于基准值的数停下,然后将prev向后移动一个位置
  3. 当prev和cur不在同一个位置时,将prev对应值与cur对应值交换
  4. 重复上面的步骤,直到cur走出数组范围
  5. 最后将基准值与prev对应位置交换

在这里插入图片描述

//前后指针法:前一个往后一个带  
private int parttion3(int[] arr,int left,int right) {  
    int pre = left;  
    int cur = left+1;  
    while(cur <= right) {  
        if(arr[cur] < arr[left] && arr[++pre] != arr[cur]) {  
            swap(arr,pre,cur);//比基准值小,且pre下一项和cur不重合,和下标处值不一样,就往后带  
        }  
        cur++;  
    }  
    swap(arr,pre,left);//最后将基准所在下标和pre所在换  
    return pre;  
}
4. 快速排序的优化

上面就是快速排序递归的三种方法。但是上面的程序其实还存在一些缺陷:对于选取的基准值的值如果是待排序数组中的边界值(最大值或最小值)的情况下,我们会进行单分支的递归,这样单分支的递归会使得递归层次变深导致不必要的消耗。

为了解决上述提到的问题,我们通常采用以下两种方法进行优化:

  1. 三数取中法
  2. 小区间优化法
//1. 三数取中法:在在起始位置,中间位置,末尾位置中选出中间值,作为基准值。使得区间分配更加平均,不会出现单分支的情况
private int getMid(int[] arr, int left, int right) {  
    int mid = (right - left) / 2 + left;  
    if(arr[left] < arr[right]) {  
        if(arr[mid] < arr[left]) {  
            return left;  
        }else if(arr[mid] > arr[right]) {  
            return right;  
        }else {  
            return mid;  
        }  
    }else {  
        if(arr[mid] > arr[left]) {  
            return left;  
        }else if(arr[mid] < arr[right]) {  
            return right;  
        }else {  
            return mid;  
        }  
    }  
}

//2. 小区间优化法:类似于二叉树,每个子树都会进行一次递归调用,越到下面递归调用会越多。为了减少递归调用,当到递归到下层时,我们可以使用其他的排序来替代。这里我们使用插入排序

经过优化后的快速排序:

public void quickSort(int[] arr) {  
    //递归过程给定区间  
    _quickSort(arr,0,arr.length-1);  
  
}  
  
private void _quickSort(int[] arr,int left,int right) {  
    if(left >= right) {  
        return ;  
    }  
    //优化:1)小区间优化法:递归到区间长度较小时,此时递归次数太多,  
    //同时小区间的数采用直接插入排序效率更高  
    if(right - left + 1 <= 7) {//小区间长度<=7时,进行优化  
        insertSortRange(arr,left,right);  
        return ;    }  
    //2)三数取中  
    int mid = getMid(arr,left,right);  
    swap(arr,left,mid);//使快排左右区间更加平均  
  
  
    //将基准排好序  
    int pivot = parttion1(arr,left,right);  
    //递归排序左右区间  
    _quickSort(arr,left,pivot-1);  
    _quickSort(arr,pivot+1,right);  
  
}

//小区间插入
private void insertSortRange(int[] arr, int left, int right) {  
    for (int i = 1+left; i <= right; i++) {  
        int tmp = arr[i];  
        int j = i-1;  
        for (; j >= left; j--) {  
            if(arr[j] > tmp) {  
                arr[j+1] = arr[j];  
            }else {  
                break;  
            }  
        }  
        //在有效下标处或不大于他的元素后放  
        arr[j+1] = tmp;  
    }  
}

private void swap(int[] arr, int i, int j) {  
    int tmp = arr[i];  
    arr[i] = arr[j];  
    arr[j] = tmp;  
  
}
5. 快速排序的非递归

快速排序的非递归形式借助栈实现,通过栈不断压入排序好基准值的左右区间。当区间元素为1时代表该区间有序:

//快排的非递归:借助栈保存区间结点  
public void quickSortNor(int[] arr) {  
    _quickSortNor(arr,0,arr.length-1);  
  
}  
  
private void _quickSortNor(int[] arr, int left, int right) { 
	//三数取中,使得区间更加平均  
	//int mid = getMid(arr,left,right);  
	//swap(arr,left,mid);
    Stack<Integer> stack = new Stack<>();  
    if(right-left < 1) {  
        return ;  
    }  
    stack.push(left);  
    stack.push(right);  
    while(!stack.isEmpty()) {  
        right = stack.pop();  
        left = stack.pop();  
        int pivot = parttion1(arr,left,right);  
        if(pivot-left >= 2) {  
            stack.push(left);  
            stack.push(pivot-1);  
        }  
        if(right-pivot >=2) {  
            stack.push(pivot+1);  
            stack.push(right);  
        }  
    }  
}

1.4 归并排序

归并排序(MERGE-SORT)是建立在归并操作上的一种有效的排序算法,该算法是采用分治法(Divide and Conquer)的一个非常典型的应用。将已有序的子序列合并,得到完全有序的序列;即先使每个子序列有序,再使子序列段间有序。若将两个有序表合并成一个有序表,称为二路归并。 归并排序核心步骤:
在这里插入图片描述

归并排序主要是将两个有序区间进行合并,那么该如何使得归并的区间是有序的是我们主要关注的问题;对于数组进行划分,不断划分,直到每个划分数组的序列中只有一个数字,当只有一个元素时,我们认为它有序。

public void mergeSort(int[] arr) {  
    int[] tmp = new int[arr.length];  
    _mergeSort(arr,tmp,0,arr.length-1);  
}  
  
//归并排序:前提:两个有序区间;    将两个有序区间合并  
private void _mergeSort(int[] arr, int[] tmp, int left, int right) {  
    if(left >= right) {//当只剩一个元素或者左边界大于右边界说明有序  
        return ;  
    }  
    int mid =( right - left) / 2 + left;  
    //使得左右区间有序  
    _mergeSort(arr,tmp,left,mid);  
    _mergeSort(arr,tmp,mid+1,right);  
    //合并两个有序区间  
    merge(arr,tmp,left,right);  
  
}

private void merge(int[] arr, int[] tmp, int left, int right) {  
    int mid = (right - left) / 2 + left;  
    int index = left;  
    int begin1 = left;  
    int begin2 = mid+1;  
    while(begin1 <= mid && begin2 <= right) {  
        if(arr[begin1] < arr[begin2]) {  
            tmp[index++] = arr[begin1++];  
        }else {  
            tmp[index++] = arr[begin2++];  
        }  
    }  
    while(begin1 <= mid) {  
        tmp[index++] = arr[begin1++];  
    }  
    while(begin2 <= right) {  
        tmp[index++] = arr[begin2++];  
    }  
    for (int i = left; i <= right; i++) {  
        arr[i] = tmp[i];  
    }  
}

归并排序特性的总结:

  1. 时间复杂度:O(N*LogN)
  2. 空间复杂度:O(N)
  3. 稳定性:稳定
归并排序的非递归

归并排序非递归:当区间为一个元素时有序。
非递归实现的思路是:逐渐把区间扩大进行排序,直到区间长度等于数组长度时排序完成

public void mergeSortNor(int[] arr) {  
    int gap = 1;  
    int[] tmp = new int[arr.length];  
    while(gap < arr.length) {  
        //每次将元素区间扩大2倍进行排序,即将原本gap大的两个有序的区间合并扩大  
        //i+=2*gap是跳到下一个待合并区间的改变条件  
        for (int i = 0; i < arr.length; i+=2*gap) {  
            int mid = i+gap-1;  
            if(mid >= arr.length) {  
                mid = arr.length-1;  
            }  
            int right = mid+gap;  
            //right= i+2*gap-1求得右边界  
            //判断右边界是否越界,越界就修正  
            if(right >= arr.length) {  
                right = arr.length-1;  
            }  
            //需要传入mid坐标,边界right值修改后可能会导致mid发生变化,所以要传mid  
            mergeNor(arr,tmp,i,mid,right);//合并两个有序区间成为一个新的大的有序区间  
        }  
        gap*=2;  
    }  
}  
private void mergeNor(int[] arr,int[] tmp,int left,int mid,int right) {  
    int begin1 = left;  
    int begin2 = mid+1;  
    int index = left;  
    while(begin1 <= mid && begin2 <= right) {  
        if(arr[begin1] < arr[begin2]) {  
            tmp[index++] = arr[begin1++];  
        }else {  
            tmp[index++] = arr[begin2++];  
        }  
    }  
    while(begin1 <= mid) {  
        tmp[index++] = arr[begin1++];  
    }  
    while(begin2 <= right) {  
        tmp[index++] = arr[begin2++];  
    }  
    for (int i = left; i <= right; i++) {  
        arr[i] = tmp[i];  
    }  
}

在非递归时,由于区间的长度可能会因为区间扩大的过程而导致越界,这时候重新矫正区间长度,在合并有效区间时Mid值会发生改变,使得不准确,所以我们将合并有序区间的方法修正,多了一个参数Mid,来记录正确Mid

1.5 计数排序

上面的排序都是基于大小的比较的排序,那么有没有不是基于数据大小的比较的排序呢?–计数排序

计数排序:适用于连续范围的数

  1. 统计相同元素出现次数
  2. 根据统计的结果将序列排序
public void countSort(int[] arr) {  
    int max = arr[0];  
    int min = arr[0];  
    for (int i = 1; i < arr.length; i++) {  
        if(max < arr[i]) {  
            max = arr[i];  
        }  
        if(min > arr[i]) {  
            min = arr[i];  
        }  
    }  
    //需要的计数数组大小==连续的数个数==max-min+1  
    int[] count = new int[max-min+1];  
    for (int i = 0; i < arr.length; i++) {  
        count[arr[i]-min]++;//使得数组从0下标开始  
    }  
    int index = 0;//从0下标开始  
    for (int i = 0; i < count.length; i++) {  
        while(count[i] != 0) {  
            arr[index++] = i+min;//i+min使数组值回到原来  
            count[i]--;  
        }  
    }  
  
}

计数排序特性的总结:

  1. 时间复杂度:O(MAX(N,range))
  2. 空间复杂度:O(range)
  3. 稳定性:稳定

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/2198181.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

CentOS 7 yum命令报错...

例如 yum install wget 可以看到是报错的 解决方案 对系统本身的 yum 源进行备份 进入源目录 cd /etc/yum.repos.d/备份 sudo cp /etc/yum.repos.d/CentOS-Base.repo /etc/yum.repos.d/CentOS-Base.repo.backup下载阿里云 CentOS 7 镜像源配置文件 sudo curl -o /etc/yum…

安装R和RStudio:开始你的数据分析之旅

数据分析是当今世界中一个非常热门的领域&#xff0c;而R语言是进行数据分析的强大工具之一。R是一种编程语言和软件环境&#xff0c;用于统计计算和图形表示。RStudio是一个集成开发环境&#xff08;IDE&#xff09;&#xff0c;它为R语言提供了一个更加友好和高效的工作环境。…

Java | Leetcode Java题解之第464题我能赢吗

题目&#xff1a; 题解&#xff1a; class Solution {Map<Integer, Boolean> memo new HashMap<Integer, Boolean>();public boolean canIWin(int maxChoosableInteger, int desiredTotal) {if ((1 maxChoosableInteger) * (maxChoosableInteger) / 2 < desi…

github创建仓库并本地使用流程,以及问题src refspec xxx does not match any

1.在 GitHub 上创建一个新仓库 登录你的 GitHub 账户。 点击右上角的 “” 按钮&#xff0c;然后选择 “New repository”。 填写仓库名称&#xff08;如 my-repo&#xff09;。 &#xff08;可选&#xff09;添加描述&#xff0c;选择是否公开或私有仓库。 &#xff08;可选&…

山羊检测系统源码分享

山羊检测系统源码分享 [一条龙教学YOLOV8标注好的数据集一键训练_70全套改进创新点发刊_Web前端展示] 1.研究背景与意义 项目参考AAAI Association for the Advancement of Artificial Intelligence 项目来源AACV Association for the Advancement of Computer Vision 研究…

探索 Python 高精度计算的奥秘:mpmath 库全解析

文章目录 探索 Python 高精度计算的奥秘&#xff1a;mpmath 库全解析背景&#xff1a;为何选择 mpmath&#xff1f;第二部分&#xff1a;mpmath 是什么&#xff1f;第三部分&#xff1a;如何安装 mpmath&#xff1f;第四部分&#xff1a;mpmath 函数使用示例第五部分&#xff1…

钢筋计:实时监测技术优化施工安全

在现代建筑工程中&#xff0c;钢筋作为结构支撑的关键材料&#xff0c;其状态直接关系到工程的安全性和耐久性。钢筋计作为一种监测工具&#xff0c;能够实时测量钢筋混凝土结构中的钢筋应力&#xff0c;从而为施工安全提供了科学依据。 了解钢筋计的原理及应用是优化施工安全的…

《恋与深空》陷抄袭争议,但不影响它登顶App Store畅销总榜

伴随着《恋与深空》全新混池而来的&#xff0c;是文案疑似抄袭的负面新闻。 9月23日&#xff0c;《恋与深空》上线了第一个国风混池“欲揽旖旎色”&#xff0c;但比玩家的夸奖与反馈更先来的&#xff0c;是男主角之一秦彻的剧情文案抄袭的争议&#xff0c;#恋与深空 抄袭#火速…

Java 表单提交:如何像 PHP 和 Python 一样简单?

在 Java 中&#xff0c;处理表单提交通常与 PHP 或 Python 中类似&#xff0c;但由于 Java 是一种强类型语言&#xff0c;处理表单提交涉及更多配置和设置。然而我将通过一些现代框架&#xff08;如 Spring Boot&#xff09;&#xff0c;Java 可以实现和 PHP、Python 一样简便的…

Study-Oracle-11-ORALCE19C-ADG集群测试

一、用户及数据测试 1、主库创建tes3用户&#xff0c;创建表test_table。备库登录test3用户并查询test_table表中数据。 -- 创建用户 CREATE USER test7 IDENTIFIED BY test7;-- 给予创建会话的权限 GRANT CREATE SESSION TO test7;-- 给予创建表的权限 GRANT CREATE TABLE TO…

前端vue-配置基地址并发送请求

1.首先&#xff0c;在HBuilder的终端下载安装luch-request 2.创建一个目录utils&#xff0c;以及下面的http.js文件&#xff0c;导入安装包&#xff0c;在new一下request&#xff0c;配置接口的基地址 3.在测试文件目录里面进行测试&#xff0c;看看请求能否发送成功&#xff…

自主主权身份在企业中的作用

随着个人数据日益商品化和集中化&#xff0c;个人重新掌控身份的需求从未如此迫切。 与此同时&#xff0c;企业使用的传统身份系统往往会将敏感信息暴露于不必要的风险中&#xff0c;使用户和组织都容易受到数据泄露和隐私侵犯。 但是&#xff0c;对于当前创建这些无尽的身份…

【3dgs】3DGS**(3D Geometry Sensing)与 **NeRF**(Neural Radiance Fields)对比

以下是 3DGS&#xff08;3D Geometry Sensing&#xff09;与 NeRF&#xff08;Neural Radiance Fields&#xff09;对比表格&#xff1a; 更加详细的资料&#xff0c;轻参考&#xff1a; NERF/3DGS 对比维度3DGS (3D Geometry Sensing)NeRF (Neural Radiance Fields)基本原理…

17.数据结构与算法-串,数组与广义表----数组的顺序存储/特殊矩阵的压缩存储

数组的定义 数组的抽象数据类型定义 数组的顺序存储 一维数组 二维数组 三维数组 n维数组 特殊矩阵的压缩存储 对称矩阵 根据该元素前面有多少个元素来判断位置 三角矩阵 对角矩阵 稀疏矩阵 双下标法 缺点&#xff1a;不能随机存取 十字链表法

Spring Boot 进阶-SpringBoot如何整合多数据源场景

对多数据源大家应该不陌生,一般的在单个应用都会存在一个数据库,一个文件存储。这里所说的数据库就是我们描述的数据源。那么多数据源的意思其实通俗来讲就是在一个单体应用中存在两个以上的数据库。这个时候就需要我们对多个数据源进行分别对待进行处理了。 理解多数据源的…

[Algorithm][贪心][整数替换][俄罗斯套娃信封问题]详细讲解

目录 1.整数替换1.题目链接2.算法原理详解1.解法一2.解法二 3.代码实现1.代码一2.代码二 2.俄罗斯套娃信封问题1.题目链接2.算法原理详解1.解法一2.解法二 3.代码实现1.代码一2.代码二 1.整数替换 1.题目链接 整数替换 2.算法原理详解 1.解法一 思路&#xff1a;模拟(递归 …

unity学习-渲染优化

cpu与gpu的区别 cpu&#xff1a;什么都干&#xff0c;主要处理代码的逻辑与传递信息&#xff0c;将需要DrewCall传递进gpu gpu&#xff1a;主要处理渲染方面&#xff0c;实现DrewCall 层级细节LOD技术 我们在unity中一个模型如果距离远了看起来就会模糊&#xff0c;但是它实…

独家揭秘!成为CSDN人工智能优质创作者:我的故事和心得

你好&#xff0c;我是三桥君 晚上我打开消息中心提醒发现&#xff0c;CSDN官方博客居然关注我了&#xff01;我又喜又惊&#xff01;喜是官方博客也认可我了&#xff01;惊是为啥关注我嘞&#xff1f; 突然想到&#xff0c;国庆放假前一天下午&#xff0c;我申请了“创作者认证…

GNURadio 平台实现SSB信号调制解调

目录 一、SSB 信号调制解调原理 二、搭建的GRC流图 一、SSB 信号调制解调原理 1.SSB调制原理 DSB信号虽然相比AM信号节约了功率利用率&#xff0c;但是信号带宽与AM信号一样&#xff0c;是基带信号最大频率的2倍。DSB信号上下边带信号完全一样&#xff0c;传递信息一样&…

Android Studio New里面没有New Flutter Project

跟着Flutter中文网的配置教程&#xff0c;安装好了flutter,在Android studio里面也安装了dart和flutter的插件。重启后还是在FIle->New里面没有显示New Flutter Project。 反复卸载重装dart和flutter插件好几次&#xff0c;依然没有效果。 原来是没有把Android APK Suppor…