Python для C # Объяснение кода - PullRequest
5 голосов
/ 24 января 2010

Моя конечная цель - преобразовать приведенный ниже код на python в C #, но я бы хотел сделать это самостоятельно, изучив синтаксис python. Я понимаю, что код является рекурсивным.

Код выдает полиномы степени n с k переменными. Более конкретно список показателей для каждой переменной.

def multichoose(n,k):
    if k < 0 or n < 0: return "Error"
    if not k: return [[0]*n]
    if not n: return []
    if n == 1: return [[k]]
    return [[0]+val for val in multichoose(n-1,k)] + \
        [[val[0]+1]+val[1:] for val in multichoose(n,k-1)]

Вот преобразование, которое у меня есть:

public double[] MultiChoose(int n, int k)
{
    if (k < 0 || n < 0)
    {
         throw new Exception();
    }

   if (k == 0)
   {
       return [[0]*n]; // I have no idea what the [[0]*n] syntax means
   }

   if (n == 0)
   {
       return new double[0]; // I think this is just an empty array
   }

   if (n == 1)
   {
       return new double[1] {k}; // I think this is just an empty array
   }

   //Part I don't understand
   return [[0]+val for val in MultiChoose(n-1,k)] + \
        [[val[0]+1]+val[1:] for val in MultiChoose(n,k-1)]
} 

Мой вопрос: как мне преобразовать код Python?

Ответы [ 4 ]

3 голосов
/ 25 января 2010

Я бы использовал LINQ в C # для перевода кода:

  • [] - пустой список.

    Enumerable.Empty<T>()
    
  • [x] - список, содержащий один элемент, х.

    Enumerable.Repeat(x, 1)
    
  • [[0]*n] - список, содержащий список, содержащий n копий 0.

    Enumerable.Repeat(Enumerable.Repeat(0, n), 1)
    
  • [X for Y in Z] является списком.

    from Y in Z select X
       - or -
    Z.Select(Y => X);
    
  • X + Y (где X и Y - списки) - объединение списков.

    Enumerable.Concat(X, Y)
    

Подпись MultiChoose будет:

 public IEnumerable<IEnumerable<double>> MultiChoose(int n, int k);
1 голос
/ 25 января 2010

Мне это показалось интригующим, и после некоторой помощи в понимании кода Python я попытался это сделать. Требуется C # 3.0 и .NET Framework 3.5.

public static IEnumerable<IEnumerable<int>> MultiChoose(int n, int k)
{
    if (k < 0 || n < 0) throw new Exception();
    if (k == 0) return Enumerable.Repeat(Enumerable.Repeat(0, n), 1);
    if (n == 0) return Enumerable.Repeat(Enumerable.Empty<int>(), 0);
    if (n == 1) return Enumerable.Repeat(Enumerable.Repeat(k, 1), 1);

    return (from val in MultiChoose(n - 1, k) select new [] { 0 }.Concat(val))
        .Concat(from val in MultiChoose(n, k - 1) select new [] { val.First() + 1 }.Concat(val.Skip(1)));
}

Вот версия на Ruby

def multichoose(n,k)
  if k<0 || n<0: raise "Error" end
  if k==0: return [[0]*n] end
  if n==0: return [] end
  if n==1: return [[k]] end
  multichoose(n-1,k).map{|val| [0]+val} + \
    multichoose(n,k-1).map{|val| [val.first+1]+val[1..-1]}
end

и некоторые примеры вывода:

>> multichoose(2,2)
=> [[0, 2], [1, 1], [2, 0]]
>> multichoose(3,2)
=> [[0, 0, 2], [0, 1, 1], [0, 2, 0], [1, 0, 1], [1, 1, 0], [2, 0, 0]]
>> multichoose(3,3)
=> [[0, 0, 3], [0, 1, 2], [0, 2, 1], [0, 3, 0], [1, 0, 2], [1, 1, 1], [1, 2, 0], [2, 0, 1], [2, 1, 0], [3, 0, 0]]
1 голос
/ 25 января 2010

Некоторые комментарии:

Питоны return "Error" не является исключением. Возвращает строковое значение «Ошибка».

Питоны if not k: не эквивалентны if (k == 0), есть еще вещи, которые "не", такие как пустые списки, значение None и т. Д. (Которые могут не иметь значения в этом случае).

Питоны foo = [for x in bar] - это понимание списка. Это эквивалентно:

foo = []
for x in bar:
   foo.append(x)
1 голос
/ 24 января 2010

[0] * n возвращает список с n 0 с. [] - пустой список. [[k]] - это список, который содержит список, содержащий k.

В последней части используются списки. Основные формы понимания списка:

[<new value> for <name> in <sequence>]
[<new value> for <name> in <sequence> if <condition>]

Создает новый список, содержащий новые значения каждый раз, когда выполняется необязательное условие.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...