英文:
Logic Clarification for sorting an array of array in python based off the value of a number using merge sort?
问题
我想根据每个内部数组中的最后一个数字,从最高值到最低值对数组中的数组进行归并排序:
arraySample=[['a', 'new', 3], ['a', 'new', 3], ['b', 'new', 1], ['c', 'old', 2], ['c', 'old', 2], ['d', 'new', 1],['a', 'new', 3],['e', 'old', 3],['e', 'old', 3],['e', 'old', 3]]
此外,我希望确保按照相同名称的元素仍然按顺序排列。
即使现在有以下代码和底部的输出:
# 归并
def merge(arr1, arr2, index):
arr3 = []
sizeA = len(arr1)
sizeB = len(arr2)
indexa = indexb = 0
while indexa < sizeA and indexb < sizeB:
if arr1[indexa][index] >= arr2[indexb][index]:
arr3.append(arr1[indexa])
indexa += 1
else:
arr3.append(arr2[indexb])
indexb += 1
arr3.extend(arr1[indexa:sizeA])
arr3.extend(arr2[indexb:sizeB])
return arr3
# 归并排序
def mergesort(array, index=-1):
size = len(array)
if size == 1:
return array
midindex = size // 2
firsthalf = array[0:midindex]
secondhalf = array[midindex:size]
firsthalf = mergesort(firsthalf, index)
secondhalf = mergesort(secondhalf, index)
array = merge(firsthalf, secondhalf, index)
return array
mergesort(arraySample)
for i in arraySample:
print(str(i)+"\n")
输出是:
['a', 'new', 3]
['a', 'new', 3]
['b', 'new', 1]
['c', 'old', 2]
['c', 'old', 2]
['d', 'new', 1]
['a', 'new', 3]
['e', 'old', 3]
['e', 'old', 3]
['e', 'old', 3]
但是预期输出是:
['a', 'new', 3]
['a', 'new', 3]
['a', 'old', 3]
['e', 'old', 3]
['e', 'new', 3]
['e', 'old', 3]
['c', 'old', 2]
['c', 'old', 2]
['b', 'new', 1]
['d', 'new', 1]
您可以通过更改归并函数的方式来解决此问题。以下是更新的代码:
# 归并
def merge(arr1, arr2, index):
arr3 = []
sizeA = len(arr1)
sizeB = len(arr2)
indexa = indexb = 0
while indexa < sizeA and indexb < sizeB:
if arr1[indexa][index] >= arr2[indexb][index]:
arr3.append(arr1[indexa])
indexa += 1
else:
arr3.append(arr2[indexb])
indexb += 1
# 在合并后,将相同名称的元素再次排序
while indexa < sizeA:
arr3.append(arr1[indexa])
indexa += 1
while indexb < sizeB:
arr3.append(arr2[indexb])
indexb += 1
return arr3
# 归并排序
def mergesort(array, index=-1):
size = len(array)
if size == 1:
return array
midindex = size // 2
firsthalf = array[0:midindex]
secondhalf = array[midindex:size]
firsthalf = mergesort(firsthalf, index)
secondhalf = mergesort(secondhalf, index)
array = merge(firsthalf, secondhalf, index)
return array
mergesort(arraySample, index=0) # 使用第一个元素(名称)进行排序
for i in arraySample:
print(str(i)+"\n")
这将按照名称进行排序,并产生您期望的输出。
英文:
I want to sort an array of array with merge sort based off the last number in each internal array from highest value to lowest value:
arraySample=[['a', 'new', 3], ['a', 'new', 3], ['b', 'new', 1], ['c', 'old', 2], ['c', 'old', 2], ['d', 'new', 1],['a', 'new', 3],['e', 'old', 3],['e', 'old', 3],['e', 'old', 3]]
In addition , I want to make sure that it is also sorted in a way such that the elements with the same name should still be ordered together .
I.e the 3 elements of 'a' should be ordered together , followed by the 3 elements of 'e' etc..
For now here is the code I have and at the bottom is the output:
Merge
def merge(arr1, arr2, index):
arr3 = []
sizeA = len(arr1)
sizeB = len(arr2)
indexa = indexb = 0
while indexa < sizeA and indexb < sizeB:
if arr1[indexa][index] >= arr2[indexb][index]:
arr3.append(arr1[indexa])
indexa += 1
else:
arr3.append(arr2[indexb])
indexb += 1
arr3.extend(arr1[indexa:sizeA])
arr3.extend(arr2[indexb:sizeB])
return arr3
Merge Sort
def mergesort(array, index=-1):
size = len(array)
if size == 1:
return array
midindex = size // 2
firsthalf = array[0:midindex]
secondhalf = array[midindex:size]
firsthalf = mergesort(firsthalf, index)
secondhalf = mergesort(secondhalf, index)
array = merge(firsthalf, secondhalf, index)
return array
mergesort(arraySample)
for i in arraySample:
print(str(i)+"\n")
Output
['a', 'new', 3]
['a', 'new', 3]
['b', 'new', 1]
['c', 'old', 2]
['c', 'old', 2]
['d', 'new', 1]
['a', 'new', 3]
['e', 'old', 3]
['e', 'old', 3]
['e', 'old', 3]
However the expected output is:
['a', 'new', 3]
['a', 'new', 3]
['a', 'old', 3]
['e', 'old', 3]
['e', 'new', 3]
['e', 'old', 3]
['c', 'old', 2]
['c', 'old', 2]
['b', 'new', 1]
['d', 'new', 1]
May I know how could improve or change the code to solve this issue? I am a beginner to Data Structures and Algorithms but I am trying to learn. Please note that I am trying to avoid the usage of external methods and libraries as well as in-built methods. Thank you !
答案1
得分: 1
你的代码目前使用 index
来确定项目的排序方式,而你使用 -1(默认值)来表示它。但是,由于你希望将第一个成员(名称)加入到排序逻辑中,你需要传递更多的信息。可以是第二个索引(这将是 0),但也许最好是将一个关键的 函数 作为参数传递。然后让该函数返回一个值(元组),用于确定给定元素的顺序。
请注意,排序后的列表由你的 mergesort
函数返回,因此主要代码应该捕获返回的列表。
以下是使用这个想法更新的代码:
def merge(arr1, arr2, key): # 接受一个关键函数作为参数
arr3 = []
sizeA = len(arr1)
sizeB = len(arr2)
indexa = indexb = 0
while indexa < sizeA and indexb < sizeB:
if key(arr1[indexa]) < key(arr2[indexb]): # 调用关键函数来确定顺序
arr3.append(arr1[indexa])
indexa += 1
else:
arr3.append(arr2[indexb])
indexb += 1
arr3.extend(arr1[indexa:])
arr3.extend(arr2[indexb:])
return arr3
def mergesort(array, key):
size = len(array)
if size == 1:
return array
midindex = size // 2
firsthalf = array[0:midindex]
secondhalf = array[midindex:size]
firsthalf = mergesort(firsthalf, key)
secondhalf = mergesort(secondhalf, key)
array = merge(firsthalf, secondhalf, key)
return array
arraySample = [['a', 'new', 3], ['e', 'old', 3], ['a', 'new', 3], ['b', 'new', 1], ['c', 'old', 2], ['c', 'old', 2], ['d', 'new', 1], ['a', 'new', 3], ['e', 'old', 3], ['e', 'old', 3]]
# 传递一个关键函数:
# 按第2个成员降序排列: `-a[2]`
# 按第0个成员升序排列: `a[0]`
result = mergesort(arraySample, lambda a: (-a[2], a[0]))
for elem in result:
print(elem)
英文:
Your code currently uses index
to determine how items should be ordered, and you use -1 (the default) for it. But as you want to add the first member (name) into the order logic, you need to pass along more information. It could be a second index (which would be 0), but maybe it is better to pass a key function as argument. Then let that function return a value (a tuple) that determines the order of the given element.
Note that the sorted list is returned by your mergesort
function, so the main code should capture that returned list.
Here is your code updated with that idea:
def merge(arr1, arr2, key): # takes a key argument
arr3 = []
sizeA = len(arr1)
sizeB = len(arr2)
indexa = indexb = 0
while indexa < sizeA and indexb < sizeB:
if key(arr1[indexa]) < key(arr2[indexb]): # call key to determine order
arr3.append(arr1[indexa])
indexa += 1
else:
arr3.append(arr2[indexb])
indexb += 1
arr3.extend(arr1[indexa:])
arr3.extend(arr2[indexb:])
return arr3
def mergesort(array, key):
size = len(array)
if size == 1:
return array
midindex = size // 2
firsthalf = array[0:midindex]
secondhalf = array[midindex:size]
firsthalf = mergesort(firsthalf, key)
secondhalf = mergesort(secondhalf, key)
array = merge(firsthalf, secondhalf, key)
return array
arraySample=[['a', 'new', 3], ['e', 'old', 3],['a', 'new', 3], ['b', 'new', 1], ['c', 'old', 2], ['c', 'old', 2], ['d', 'new', 1],['a', 'new', 3],['e', 'old', 3],['e', 'old', 3]]
# Pass a key function:
# descending by member 2: `-a[2]`
# ascending by member 0: `a[0]`
result = mergesort(arraySample, lambda a: (-a[2], a[0]))
for elem in result:
print(elem)
通过集体智慧和协作来改善编程学习和解决问题的方式。致力于成为全球开发者共同参与的知识库,让每个人都能够通过互相帮助和分享经验来进步。
评论