views:

264

answers:

4

Hello. I need an advice about how to create new string array from 4 different string arrays:

We have 4 string arrays:

string[] arr1 = new string []  {"a1","a2","a3"..., "a30"};  
string[] arr2 = new string []  {"d10","d11","d12","d13","d14","d15"};  
string[] arr3 = new string []  {"f1","f2","f3"...,"f20"};  
string[] arr4 = new string []  {"s10","s11","s12","s13","s14"};  

We need to add all string elements of all 4 arrays with each other like this:

a1+d10+f1+s10  
a2+d10+f1+s10

...       
a1+d11+f1+s10  
a2+d11+f1+s10  
...  
a30+d15+f20+s14

I mean all combinations in that order : arr1_element, arr2_element, arr3_element, arr4_element
So the result array would be like that:
string[] arr5 = new string [] {"a1d10f1s10","a2d10f1s10 "....};

Any help would be good Thank you

+1  A: 

Make a recursive method that returns all combinations of the arrays:

static IEnumerable<string> GetCombinations(string[][] arrays, int len, string start) {
  foreach (string s in arrays[len - 1]) {
    if (len == 1) {
      yield return s + start;
    } else {
      foreach (string r in GetCombinations(arrays, len - 1, s + start)) {
        yield return r;
      }
    }
  }
}

Usage:

string[][] arrays = { arr1, arr2, arr3, arr4 };
foreach (string s in GetCombinations(arrays, arrays.Length, string.Empty)) {
  Console.WriteLine(s);
}
Guffa
Thank you for fast and valuable reply. Looks like it should work fine but it results only the last string. I dont know what am i doing wrong.
new_coder
@new_coder: The code is tested and it does return all the combinations. Note that the method doesn't put all combinations into a huge collection, instead it returns one combination at a time. You have to loop through the result and handle each string at a time.
Guffa
Thank you for your note. I am new to programming can you link me where can i read about how to "to loop through the result and handle each string at a time" or give me an example please. Many many thanks!
new_coder
Thank you for your code - it solved the problem!
new_coder
A: 

Something similar to this might work...

List<string> AddEntries(List<List<string>> entries) {
   List<string> finalEntries = new List<string>();

   if (entries != null && entries.Length > 0) {
      if (entries.Length > 1) {
         foreach(string entry in entries) {
            foreach(string subentry in AddEntries(entries.Skip(1)) {
               finalEntries.Add(entry + subEntry);
            }
         }
      } else {
         foreach(string entry in entries[0]) { finalEntries.add(entry); }
      }
   }
   return finalEntries;
}

I apologize for the code, I dont have a compiler here to test. Assumes that you are using C# 3.5 with extension methods. I took the liberty of changing your string[] to List. If you arent using 3.5 you will need to write your own function for trimming the nested arrays down.

GrayWizardx
I think you mean .NET 3.5 or C# 3.0. There's no such thing as C# 3.5. There's also no sign of extension methods in your code...
Jon Skeet
Yes @Jon Skeet, I meant framework 3.5, my bad for typing so fast. Entries.Skip() I thought was an extension since it is not part of the default List<T> implementation.
GrayWizardx
@GrayWizardx: Ah yes, I hadn't seen the call to Skip.
Jon Skeet
A: 

Hi, you need to use C# 4.0 .Zip() Extension method for IEnumerable<> collections. The method takes deleagate as parameter for that purpose. Sample:

   List<string> a = new List<string> { "code" };
   List<int> b = new List<int>() { 7 };
   var res =  a.Zip(b, (p1, p2) => p1.ToString() + p2.ToString());
portland
You should read up on what the method does. It doesn't create combinations between the items, it only pairs up the items with the same index.
Guffa
Guffa, i provided a sample for you.
portland
@portland: You are missing the point completely. I wasn't asking for an example, I was pointing out that the method doesn't do what the OP asked for.
Guffa
+1  A: 

Once upon a time in a programming contest I used this. It worked fine. See if it works for you.

:)

 private static IEnumerable<string> 
    GetCombinations(string[] arr1, string[] arr2, string[] arr3, string[] arr4)
        {
            int i, j, k, l;
            i = j = k = l = 0;

            for (i = 0; i < arr4.Length; i++)
                for (j = 0; j < arr3.Length; j++)
                    for (k = 0; k < arr2.Length; k++)
                        for (l = 0; l < arr1.Length; l++)
                            yield return (arr1[l] + arr2[k] + arr3[j] + arr4[i]);

        }

Sample usage:

public static void Main(string[] args)
{
    string[] arr1 = new string[] { "a1", "a2", "a3", "a30" };
    string[] arr2 = new string[] { "d10", "d11", "d12", "d13" };
    string[] arr3 = new string[] { "f1", "f2", "f3", "f20" };
    string[] arr4 = new string[] { "s10", "s11", "s13", "s14" };


    var list = GetCombinations(arr1, arr2, arr3, arr4);

    foreach (var item in list.Take<string>(10))
    {
        Console.WriteLine(item);
    }
}
TheMachineCharmer
Thank you for your reply. This is amazing "compact" code!:) and it seems that it should work - but i have the same problem it results only last string
new_coder
I wanted to `yield return` it but my internet connection was down for the day. Done now. :)
TheMachineCharmer
Thank you for your help! Your code is working correctly and is very usefull.
new_coder