Как я использую Основную теорему для описания рекурсии?

Я рекомендую разделять код и данные (жесткое кодирование - очень плохая практика). Поэтому плохая идея жестко кодировать группировку в массиве Arr=(Array("A", 1), Array("B",2), Array("C",3)). Вместо этого вы хотели бы сохранить эти данные в (возможно, скрытом) листе.

Таким образом, ваш лист GroupLookup будет выглядеть так

column A    column B
A            1
B            2
C            3

Тогда вы можете использовать простую функцию VLOOKUP в вашем листе данных

column A   column B
A          =VLOOKUP(A:A,GroupLookup!A:B,2,FALSE)
B
C
A 
...

[ 1113] Измените из-за комментария:

Если вам нужно сделать это с VBA, все равно поместите свой GroupLookup в лист, а не в код! Например, в вашу надстройку или куда-либо еще вы добавляете свой макрос, но следующий лист:

Итак, ваш лист GroupLookup будет выглядеть так

column A    column B
A            1
B            2
C            3

И ищите группы в этом лист с методом WorksheetFunction.VLookup

Option Explicit 

Sub WriteGroups()
    Dim GroupLookup As Worksheet 'define workbook/sheet where the group lookup table is
    Set GroupLookup = ThisWorkbook.Worksheets("GroupLookup")


    With Workbooks("YourWb").ActiveSheet 'this is the sheet where the group is written to
        Dim LastRow As Long
        LastRow = .Cells(.Rows.Count, "A").End(xlUp).Row

        Dim iRow As Long
        For iRow = 1 To LastRow
            On Error Resume Next
            .Cells(iRow, "B").Value = Application.WorksheetFunction.Vlookup(.Cells(iRow, "A").Value, GroupLookup.Range("A:B"), 2, False)
            If Err.Number <> 0 Then .Cells(iRow, "B").Value = CVErr(xlErrNA) 'write #NA if group not found
            On Error Goto 0
        Next iRow
    End With

End Sub

6
задан Dukeling 28 September 2013 в 12:28
поделиться

5 ответов

Несколько лет назад Mohamad Akra и Louay Bazzi доказали результат, который обобщает Основной метод - это почти всегда лучше. Вы действительно не должны использовать Основную Теорему больше...

Посмотрите, например, эту рецензию: http://courses.csail.mit.edu/6.046/spring04/handouts/akrabazzi.pdf

В основном заставьте свое повторение быть похожим на уравнение 1 в газете, собрать коэффициенты и интегрировать выражение в Теореме 1.

8
ответ дан 8 December 2019 в 18:43
поделиться

Ваш метод, записанный в коде с помощью рекурсивной функции, был бы похож на это:

function r(int n) 
{
  if (n == 2) return 1;
  if (n == 1) return 1;
  return 2 * r(n-2) + r(n-1);  // I guess we're assuming n > 2
}

Я не уверен, каково "повторение", но рекурсивная функция является просто той, которая называет себя.

Для рекурсивных функций нужен пункт Escape (некоторый нерекурсивный случай - например, "если n == 1 возврат 1") для предотвращения Ошибки переполнения стека (т.е. функция вызвана так, что интерпретатор исчерпывает память или другие ресурсы),

1
ответ дан 8 December 2019 в 18:43
поделиться

Простая программа, которая реализовала бы, который будет похож:

public int r(int input) {
    if (input == 1 || input == 2) {
        return 1;
    } else {
        return 2 * r(input - 2) + r(input -1)
    }
}

Необходимо было бы также удостовериться, что вход не собирается вызывать бесконечную рекурсию, например, если вход вначале был меньше чем 1. Если это не допустимый случай, то возвратите ошибку, если это допустимо, то возвратите соответствующее значение.

1
ответ дан 8 December 2019 в 18:43
поделиться

«Я не совсем уверен, что такое« повторение »

Определение« рекуррентного отношения »- это последовательность чисел,« домен которой представляет собой некоторый бесконечный набор целых чисел и диапазон которых представляет собой набор действительных чисел ". С дополнительным условием, что функция, описывающая эту последовательность, «определяет один член последовательности в терминах предыдущего».

И цель их решения, я думаю, состоит в том, чтобы перейти от рекурсивного определения к определению, которое нет. Скажем, если бы у вас были T (0) = 2 и T (n) = 2 + T (n-1) для всех n> 0, вам пришлось бы перейти от выражения «T (n) = 2 + T (n -1) "такому как" 2n + 2 ".

источники: 1) «Дискретная математика с теорией графов - второе издание», Эдгар Г. Гудэр и Майкл М. Парментер. 2) «Компьютерные алгоритмы C ++» Эллиса Хоровица, Сартаджа Сахни и Сангутевара Раджасекарана.

1
ответ дан 8 December 2019 в 18:43
поделиться

Захари:

Допустим, вам дано это повторение:

r (n) = 2 * r (n-2) + r (n-1); г (1) = г (2) = 1

Действительно ли это в виде основная теорема? Если да, то на словах что это говорит?

Я думаю, что ваше рекуррентное отношение говорит о том, что для функции «r» с параметром «n» (представляющим общее количество вводимых вами наборов данных) все, что вы получаете в n-я позиция набора данных - это результат n-1-й позиции плюс два раза, что является результатом n-2-й позиции, без нерекурсивной работы. Когда вы пытаетесь решить рекурсивное отношение, вы пытаетесь выразить его таким образом, чтобы не было рекурсии.

Однако я не думаю, что это правильная форма для метода основной теоремы. Ваше утверждение представляет собой «линейное рекуррентное отношение второго порядка с постоянными коэффициентами». По-видимому, согласно моему старому учебнику по дискретной математике, это та форма, которая вам нужна для решения рекуррентного отношения.

Вот форма, которую они придают:

r(n) = a*r(n-1) + b*r(n-2) + f(n)

Поскольку 'a' и 'b' - некоторые константы, а f (n) - некоторая функция от n. В вашем утверждении a = 1, b = 2 и f (n) = 0. Всякий раз, когда f (n) равно нулю, рекуррентное отношение называется «однородным». Итак, ваше выражение лица однородно.

Я не думаю, что вы можете решить гомогенное рекуррентное отношение, используя Теорему мастер-метода, потому что f (n) = 0. Ни один из случаев теоремы об основном методе не допускает этого, потому что n-в-степени-из -ничего не может равняться нулю.Я могу ошибаться, потому что на самом деле я не эксперт в этом, но я не знаю, что можно решить однородное рекуррентное отношение с помощью основного метода.

Я считаю, что способ решения однородного рекуррентного отношения состоит из 5 шагов:

1) Сформируйте характеристическое уравнение, которое имеет вид:

x^k - c[1]*x^k-1 - c[2]*x^k-2 - ... - c[k-1]*x - c[k] = 0

Если у вас есть только 2 рекурсивных экземпляров в вашем однородном рекуррентном соотношении, то вам нужно только преобразовать ваше уравнение в квадратное уравнение, где

x^2 - a*x - b = 0

Это потому, что рекуррентное отношение формы

r(n) = a*r(n-1) + b*r(n-2)

может быть переписано как

r(n) - a*r(n-1) - b*r(n-2) = 0

2) После вашего рекуррентного отношения переписывается как характеристическое уравнение, затем находятся корни (x [1] и x [2]) характеристического уравнения.

3) С вашими корнями ваше решение теперь будет одной из двух форм:

if x[1]!=x[2]
    c[1]*x[1]^n + c[2]*x[2]^n
else
    c[1]*x[1]^n + n*c[2]*x[2]^n

для, когда n> 2. 4) В новой форме вашего рекурсивного решения вы используете начальные условия (r (1) и r (2)), чтобы найти c [1] и c [2]

. пример вот что мы получаем:

1) г (п) = 1 * г (п-1) + 2 * г (п-2) => x ^ 2 - x - 2 = 0

2) Решение относительно x

x = (-1 +- sqrt(-1^2 - 4(1)(-2)))/2(1)

    x[1] = ((-1 + 3)/2) = 1
    x[2] = ((-1 - 3)/2) = -2

3) Поскольку x [1]! = x [2], ваше решение имеет вид:

c[1](x[1])^n + c[2](x[2])^n

4) Теперь используйте ваши начальные условия для нахождения двух констант c [1] и c [2]:

c[1](1)^1 + c[2](-2)^1 = 1
c[1](1)^2 + c[2](-2)^2 = 1

Честно говоря, я не уверен, каковы ваши константы в этой ситуации, я остановился на этом месте. Я предполагаю, что вам придется подставлять числа, пока вы каким-то образом не получите значения для c [1] и c [2], которые удовлетворяли бы этим двум выражениям.Либо так, либо выполните сокращение строк в матрице C, где C равно:

[ 1 1   | 1 ]
[ 1 2   | 1 ] 

Zachary:

Повторение, которое описывает наилучшим образом способ количество операций сложения в следующем фрагменте программы (при вызове с l == 1 и r == n)

int example(A, int l, int r) {
  if (l == r)
    return 2;
  return (A[l] + example(A, l+1, r);
}

Вот значения временной сложности для вашего данного кода, когда r> l:

int example(A, int l, int r) {      =>  T(r) = 0
  if (l == r)               =>  T(r) = 1
    return 2;               =>  T(r) = 1
  return (A[l] + example(A, l+1, r);    =>  T(r) = 1 + T(r-(l+1))
}

Total:                      T(r) = 3 + T(r-(l+1))

Иначе, когда r == l, то T (r) = 2, потому что для оператора if и return требуется 1 шаг на выполнение.

2
ответ дан 8 December 2019 в 18:43
поделиться
Другие вопросы по тегам:

Похожие вопросы: