Created
April 20, 2012 16:25
-
-
Save AlbertoMonteiro/2430114 to your computer and use it in GitHub Desktop.
Trying to simulate list comprehension of Python in C#
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
using System; | |
using System.Collections.Generic; | |
using System.Linq; | |
namespace ConsoleApplication3 | |
{ | |
public class Comprehension | |
{ | |
public Comprehension() | |
{ | |
Lists = new Dictionary<string, IEnumerable<dynamic>>(); | |
} | |
private IDictionary<string, IEnumerable<dynamic>> Lists { get; set; } | |
public Comprehention In(string listAlias, IEnumerable<object> list) | |
{ | |
Lists.Add(listAlias, list); | |
return this; | |
} | |
public IEnumerable<dynamic> Select(Func<IDictionary<string, dynamic>, dynamic> action) | |
{ | |
var keepGoing = true; | |
var maxInEachList = Lists.Select(list => list.Value.Count()).ToList(); | |
var currentIndexInEachList = new List<int>(); | |
for (var i = 0; i < maxInEachList.Count(); i++) | |
currentIndexInEachList.Add(0); | |
var keys = Lists.Select(x => x.Key).ToList(); | |
while (keepGoing) | |
{ | |
var currentObj = new Dictionary<string, dynamic>(); | |
for (var j = 0; j < keys.Count; j++) | |
{ | |
var key = keys[j]; | |
currentObj.Add(key, Lists[key].ElementAt(currentIndexInEachList[j])); | |
if (j + 1 == currentIndexInEachList.Count) | |
currentIndexInEachList[j]++; | |
if (currentIndexInEachList[j] == maxInEachList[j]) | |
{ | |
if (j - 1 < 0) | |
{ | |
for (var indx = 0; indx < currentIndexInEachList.Count; indx++) | |
currentIndexInEachList[indx] = 0; | |
} | |
else | |
{ | |
currentIndexInEachList[j - 1]++; | |
currentIndexInEachList[j] = 0; | |
FixList(currentIndexInEachList, maxInEachList); | |
} | |
} | |
} | |
for (var i = 0; i < maxInEachList.Count; i++) | |
{ | |
keepGoing = keepGoing && maxInEachList[i] != currentIndexInEachList[i]; | |
if (keepGoing) | |
break; | |
} | |
yield return action(currentObj); | |
} | |
} | |
private static void FixList(IList<int> currentIndex, IList<int> maxInEachList) | |
{ | |
var @fixed = false; | |
for (var i = 0; i < currentIndex.Count; i++) | |
{ | |
if (currentIndex[i] == maxInEachList[i]) | |
{ | |
if (i - 1 < 0) | |
{ | |
for (var indx = 0; indx < currentIndex.Count; indx++) | |
currentIndex[indx] = maxInEachList[0]; | |
break; | |
} | |
currentIndex[i - 1]++; | |
currentIndex[i] = 0; | |
@fixed = true; | |
} | |
} | |
if (@fixed) | |
FixList(currentIndex, maxInEachList); | |
} | |
} | |
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
list1 = [ "a", "b", "c" ] | |
list2 = [ 1, 2, 3 ] | |
list3 = [ "!", "@", "#" ] | |
list4 = [ "9", "8", "7" ] | |
li = [[a,b,c,d] for a in list1 for b in list2 for c in list3 for d in list4] | |
print li |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
using System; | |
using System.Linq; | |
namespace ConsoleApplication3 | |
{ | |
class Program | |
{ | |
private static void Main(string[] args) | |
{ | |
var list1 = new dynamic[] { "a", "b", "c" }; | |
var list2 = new dynamic[] { 1, 2, 3 }; | |
var list3 = new dynamic[] { "!", "@", "#" }; | |
var list4 = new dynamic[] { "9", "8", "7" }; | |
var withLinq = from a in list1 | |
join b in list2 on true equals true | |
join c in list3 on true equals true | |
join d in list4 on true equals true | |
select new[] { a, b, c, d }; | |
var comprehention = new Comprehension(); | |
var withComprehension = comprehension | |
.In("a", list1) | |
.In("b", list2) | |
.In("c", list3) | |
.In("d", list4) | |
.Select(l => new[] { l["a"], l["b"], l["c"], l["d"] }); | |
foreach (var item in withComprehension) | |
Console.WriteLine("({0},{1},{2},{3})", item[0], item[1], item[2], item[3]); | |
Console.WriteLine(withComprehension.Count()); | |
} | |
} | |
} |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment