我正在嘗試解決這個 LeetCode 問題。
給定兩個整數陣列 nums1 和 nums2,按非遞減順序排序,以及兩個整數 m 和 n,分別表示 nums1 和 nums2 中的元素個數。
將 nums1 和 nums2 合并為一個按非降序排序的陣列。
最終的排序陣列不應由函式回傳,而是存盤在陣列 nums1 中。為了適應這一點,nums1 的長度為 m n,其中前 m 個元素表示應該合并的元素,最后 n 個元素設定為 0 并且應該被忽略。nums2 的長度為 n。
Input: nums1 = [1,2,3,0,0,0], m = 3, nums2 = [2,5,6], n = 3
Output: [1,2,2,3,5,6]
我下面的解決方案在我的 Mac 上的 vscode 上運行良好,但是當我在 leetcode 上使用完全相同的測驗用例運行它時,它會引發編譯錯誤。有誰知道為什么?
/// my solution
void merge(int* nums1, int nums1Size, int m, int* nums2, int nums2Size, int n){
int i = m - 1;
int j = n - 1;
int k = nums1Size - 1;
while(k >= 0){
if (nums1[i] < nums2[j]){
nums1[k--] = nums2[j--];
} else {
nums1[k--] = nums1[i--];
}
}
}
int main(void){
int arr1[] = {1, 2, 3, 0, 0};
int arr2[] = {5, 6};
merge(arr1, 5, 3, arr2, 2, 2);
for (int i = 0; i < 5; i ){
printf("%i\n", arr1[i]);
}
}
此代碼正確列印 1,2,3,5,6。
但是當我給出相同的輸入時,在 leetcode 上,它顯示
==31==ERROR: AddressSanitizer: heap-buffer-overflow on address 0x60200000000c at pc 0x564b115dfc07 bp 0x7ffecbbcf300 sp 0x7ffecbbcf2f0
READ of size 4 at 0x60200000000c thread T0
#2 0x7f4f899f30b2 in __libc_start_main (/lib/x86_64-linux-gnu/libc.so.6 0x270b2)
0x60200000000c is located 4 bytes to the left of 8-byte region [0x602000000010,0x602000000018)
allocated by thread T0 here:
#0 0x7f4f8a638bc8 in malloc (/lib/x86_64-linux-gnu/libasan.so.5 0x10dbc8)
#3 0x7f4f899f30b2 in __libc_start_main (/lib/x86_64-linux-gnu/libc.so.6 0x270b2)
Shadow bytes around the buggy address:
0x0c047fff7fb0: 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00
0x0c047fff7fc0: 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00
0x0c047fff7fd0: 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00
0x0c047fff7fe0: 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00
0x0c047fff7ff0: 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00
=>0x0c047fff8000: fa[fa]00 fa fa fa fa fa fa fa fa fa fa fa fa fa
0x0c047fff8010: fa fa fa fa fa fa fa fa fa fa fa fa fa fa fa fa
0x0c047fff8020: fa fa fa fa fa fa fa fa fa fa fa fa fa fa fa fa
0x0c047fff8030: fa fa fa fa fa fa fa fa fa fa fa fa fa fa fa fa
0x0c047fff8040: fa fa fa fa fa fa fa fa fa fa fa fa fa fa fa fa
0x0c047fff8050: fa fa fa fa fa fa fa fa fa fa fa fa fa fa fa fa
Shadow byte legend (one shadow byte represents 8 application bytes):
Addressable: 00
Partially addressable: 01 02 03 04 05 06 07
Heap left redzone: fa
Freed heap region: fd
Stack left redzone: f1
Stack mid redzone: f2
Stack right redzone: f3
Stack after return: f5
Stack use after scope: f8
Global redzone: f9
Global init order: f6
Poisoned by user: f7
Container overflow: fc
Array cookie: ac
Intra object redzone: bb
ASan internal: fe
Left alloca redzone: ca
Right alloca redzone: cb
Shadow gap: cc
==31==ABORTING
uj5u.com熱心網友回復:
想象一下這樣的情況:
nums1 = {10, 11, 12, 0, 0, 0};
nums2 = {1, 2, 3};
在 while 回圈中的某個時刻, indexi將變為-1并且 indexj將變為2,您將比較nums1[-1] and nums2[2]哪個會導致錯誤。而且您還忘記了在 while 回圈之后可能有一些元素沒有插入nums1. 我認為這段代碼將幫助您更好地理解:
void merge(int* nums1, int nums1Size, int m, int* nums2, int nums2Size, int n){
int i = m - 1, j = n - 1, k = nums1Size - 1;
while(i >= 0 && j >= 0){
if (nums1[i] < nums2[j]){
nums1[k--] = nums2[j--];
} else {
nums1[k--] = nums1[i--];
}
}
while (i >= 0) nums1[k--] = nums1[i--];
while (j >= 0) nums1[k--] = nums2[j--];
}
我建議你在紙上執行你的代碼,看看錯誤在哪里。
轉載請註明出處,本文鏈接:https://www.uj5u.com/yidong/476936.html
