Я работаю над сценарием C # в рамках проекта Unity3D, где я пытаюсь взять список строк и получить 2D-список перестановок. Используя этого ответа GetPermutations()
следующим образом:
List<string> ingredientList = new List<string>(new string[] { "ingredient1", "ingredient2", "ingredient3" });
List<List<string>> permutationLists = GetPermutations(ingredientList, ingredientList.Count);
Но выдает неявную ошибку преобразования:
IEnumerable<IEnumerable<string>> to List<List<string>> ... An explicit conversion exists (are you missing a cast)?
Итак, я посмотрел несколько мест, таких как здесь , и предложил следующую модификацию:
List<List<string>> permutationLists = GetPermutations(ingredientList, ingredientList.Count).Cast<List<string>>().ToList();
Но он ломается во время выполнения, обрабатывается внутри и позволяет продолжить работу без указания сбоя - возможно, потому, что он работает в Unity3D.
Вот что я вижу в Unity3D после остановки отладки скрипта:
InvalidCastException: Cannot cast from source type to destination type.
System.Linq.Enumerable+<CreateCastIterator>c__Iterator0`1[System.Collections.Generic.List`1[System.String]].MoveNext ()
System.Collections.Generic.List`1[System.Collections.Generic.List`1[System.String]].AddEnumerable (IEnumerable`1 enumerable) (at /Users/builduser/buildslave/mono/build/mcs/class/corlib/System.Collections.Generic/List.cs:128)
System.Collections.Generic.List`1[System.Collections.Generic.List`1[System.String]]..ctor (IEnumerable`1 collection) (at /Users/builduser/buildslave/mono/build/mcs/class/corlib/System.Collections.Generic/List.cs:65)
System.Linq.Enumerable.ToList[List`1] (IEnumerable`1 source)
Который я интерпретирую как все еще неверное приведение, поэтому я также попробовал следующие подходы и больше, что я не могу вспомнить:
List<List<string>> permutationLists = GetPermutations(ingredientList, ingredientList.Count).Cast<List<List<string>>>();
List<List<string>> permutationLists = GetPermutations(ingredientList.AsEnumerable(), ingredientList.Count);
, а также явное приведение к круглым скобкам перед вызовом метода, как в C или Java, но безрезультатно.
Итак, как я должен приводить результаты функции GetPermutations()
, чтобы получить List<List<string>>
? Или, в качестве альтернативы, как я могу изменить функцию, чтобы она возвращала только List<List<string>>
, поскольку она не нужна для работы с универсальным типом? Я попытался изменить метод сам, чтобы он был следующим:
List<List<string>> GetPermutations(List<string> items, int count)
{
int i = 0;
foreach(var item in items)
{
if(count == 1)
yield return new string[] { item };
else
{
foreach(var result in GetPermutations(items.Skip(i + 1), count - 1))
yield return new string[] { item }.Concat(result);
}
++i;
}
}
Однако, удалив <T>
из имени функции, он ломается, заявляя, что тело не может быть блоком итератора. У меня нет опыта работы с C #, и я не очень разбираюсь в функциях шаблонов в строго типизированных языках, поэтому любые объяснения / помощь приветствуются.
Я не был уверен, как искать эту проблему, поэтому, если это дубликат, просто опубликуйте его здесь, и я немедленно удалю это сообщение.