Quicksort返回相同的向量传递

时间:2014-05-24 01:59:13

标签: r parameter-passing pass-by-reference pass-by-value

我最近开始使用R并尝试实施快速排序。我正在使用“算法导论(第3版)”一书

我正在使用RStudio并且没有看到任何错误,但它会返回相同的向量,我会假设出错了吗?我相信我的代码与本书的伪代码相匹配。 Psuedo代码如下:

Partition(A, p, r)
  x = A[r]
  i = p - 1
  for j = p to r - 1
     if A[j] <= x
       i = i + 1
       swap(A[i], A[j])
  swap(A[i+1], A[r]
  return i + 1

Quicksort(A, p, r)
  if p < r
    q = Partition(A, p, r)
    Quicksort(A, p, q - 1)
    Quicksort(A, q + 1, r)

我在R中写了相同的两个函数:

partition <- function(a, p, r) {
    x = a[r]
    i = p - 1
    for (j in p:(r-1)) {
        if (a[j] <= x) {
            i = i + 1
            t = a[i]
            a[i] = a[j]
            a[j] = t
        }
    }
    t = a[i+1]
    a[i+1] = a[r]
    a[r] = t
    i+1
}

quicksort <- function(a, p, r) {
    if (p < r) {
        q = partition(a, p, r)
        quicksort(a, p, q-1)
        quicksort(a, q+1, r)
    }
    a
}

RStudio中,我获取文件并使用我创建的矢量调用它:

> v
[1] 8 5 6 7 4 1 3 2
> quicksort(v, 1, length(v))
[1] 8 5 6 7 4 1 3 2

据我所知,你可以在R中做递归函数,我知道你不能通过引用传递,但是这不会用更改的向量调用相同的函数吗?我很困惑为什么它返回相同的矢量传递。任何帮助将不胜感激。

2 个答案:

答案 0 :(得分:1)

每次要使用函数更改对象时,都必须将其返回并进行分配。我在两个地方更改了您的代码:partition函数返回两个项目的列表,向量a和位置i。在quicksort中:partition的结果最初存储在temp中,其项目已分配到aq。此外,您必须将a的每次更改的结果分配给它。

partition <- function(a, p, r) {
  x = a[r]
  i = p - 1
  for (j in p:(r-1)) {
    if (a[j] <= x) {
      i = i + 1
      t = a[i]
      a[i] = a[j]   
      a[j] = t
    }
  }
  t = a[i+1]
  a[i+1] = a[r]
  a[r] = t
  list(i = i+1, a = a)
}

quicksort <- function(a, p, r) {
  if (p < r) {
    temp = partition(a, p, r)
    a <- temp$a
    q = temp$i
    a = quicksort(a, p, q-1)
    a = quicksort(a, q+1, r)
  }
  a
}

v = c(8, 5, 6, 7, 4, 1, 3, 2)
quicksort(v, 1, length(v))
## [1] 1 2 3 4 5 6 7 8

干杯,

亚历

答案 1 :(得分:0)

这是因为您未在函数aquicksort中修改partition。 R(实际上)按值传递。修改函数中的值时,您正在修改副本。函数返回后,此修改不会保留。

因此,您需要返回分区值,而不是在parition内进行修改,以使其正常工作。

例如,partition可以返回两个向量的列表,即两个分区。然后,您可以在每个返回的向量上调用quicksort