2011-08-11 8 views
0

オブジェクトリストから一意のオブジェクトタプルを作成するために必要な以下の課題があります。ダイナミックなリスト・サイズ(n次元)のためにこれをどうやって行うことができるかは、ここでは争点になっていますか?固定寸法の場合は簡単です。誰かが第三者のAPIを知っているか、私がどのようにこれに到達できるかについてのヒントを願っています。Java - 一意のオブジェクトタプル(n次元)を作成する方法は?

以下の例では3つのリストを示しているため、説明が簡単です。 私はオブジェクトをそのクラスでソートしてリストに入れました。

各オブジェクトが相互に一度ペアリングされているように、私は、以下のタプルを持ちたい
lista = {a1,a2} 
listb = {b1,b2,b3} 
listc = {c1,c2} 

tuple1 = {a1,b1,c1} 
tuple2 = {a1,b1,c2} 
tuple3 = {a1,b2,c1} 
tuple4 = {a1,b2,c2} 
tuple5 = {a1,b3,c1} 
tuple6 = {a1,b3,c2} 
tuple7 = {a2,b1,c1} 
tuple8 = {a2,b1,c2} 
tuple9 = {a2,b2,c1} 
tuple10 = {a2,b2,c2} 
tuple11 = {a2,b3,c1} 
tuple12 = {a2,b3,c2} 

どのように私はケース
にすることを達成することができます - リストの数を動的に
です - リストのサイズは動的です

ヒントやアイデアはありますか?事前にありがとう

+0

アルゴリズムの宿題のように聞こえます。あなたはこれを達成するための特定のアルゴリズムを使用するように言われましたか? – doNotCheckMyBlog

+0

ちょっとした問題ですが解決できます。リストの数が固定されると簡単になります。 Pythonでは、この場合、1行である: '[(a、b、c)listbのリストbのリストbのリストbのc]' :-) –

+0

残念ながら、私はどのアルゴリズムを使うことができないのか分からないこのため。あなたはアイデアがあれば?リストの数は固定されていません。それ以外の場合は簡単にコーディングできます。ありがとうございます – Mark

答えて

2

次のようにソリューションを構築できます。最初は、現代の言語ではリストのサイズが変わることは決して問題ではないことに注意してください。現実にはすべての言語が今日可変サイズのリストをサポートしているからです。より難しいのは、リストの数が異なる場合です。ここで

は、リストの固定数のためのPythonのケースです:Java用

lista = ["a1","a2"] 
listb = ["b1","b2","b3"] 
listc = ["c1","c2"] 
[(a,b,c) for a in lista for b in listb for c in listc] 

は同じことを行います。あなたは、forループのネストされた3が必要になります。

List<String> lista = Arrays.asList("a1","a2"); 
List<String> listb = Arrays.asList("b1","b2","b3"); 
List<String> listc = Arrays.asList("c1","c2"); 

List<List<String>> result = new ArrayList<List<String>>(); 
for (String a: lista) { 
    for (String b: listb) { 
     for (String c: listc) { 
      result.add(Arrays.asList(a, b, c)); 
     } 
    } 
} 
System.out.println(result); 

これは

[[a1, b1, c1], [a1, b1, c2], [a1, b2, c1], [a1, b2, c2], [a1, b3, c1], [a1, b3, c2], [a2, b1, c1], [a2, b1, c2], [a2, b2, c1], [a2, b2, c2], [a2, b3, c1], [a2, b3, c2]] 

を生み出す今トリックはあなたがforループの不確定数を行うのですかですか? 1つの方法は、再帰を使用することです。

0リスト(または1つ)のベースケースから始め、次に自分自身に質問します。新しいリストを追加すると、結果はどのように変わるのですか?それで、素敵な小さな再帰的な定式をまとめることができます。これで助けが必要ですか?

(脇:Pythonでは、私たちは物事のこれらの種類のitertoolsを持っている私は、任意のJavaアナログを認識していないですが、いくつかのグーグルが何かを上げるかもしれない。。)

大丈夫ですが、無制限の数のための再帰的製剤を開発しましょうリストの。リストが1つだけの場合は、

a = ["a1", "a2"] 

となり、結果は[["a1"],["a2"]]となります。しかし別のリストを追加しましょう:

a = ["b1", "b2"] 

答えは今ですか?

[[a1, b1], [a1, b2], [a2, b1], [a2, b2]] 

これをどのように取得しましたか?答えは、新しいリストの各要素を取り出し、それを結果の各要素に追加することです。新しいリストを追加するたびに同じことをします。ここに["c1","c2","c3"]を追加するとします。私たちは何を得るのか見ていますか?その場合、再帰的なステップを定義できるようになりました!私は抵抗することができませんでし

COMPLETE CODE

大丈夫!どうぞ。

import java.util.ArrayList; 
import java.util.Arrays; 
import java.util.List; 

/** 
* An application requested by a SO user. 
*/ 
public class ProductExample { 

    /** 
    * Returns a list containing all possible products of a list of lists of strings. 
    */ 
    public static List<List<String>> product(List<List<String>> lists) { 
     List<List<String>> result = new ArrayList<List<String>>(); 

     if (lists.isEmpty()) { 
      result.add(new ArrayList<String>()); 
      return result; 
     } 

     List<List<String>> partial = product(lists.subList(0, lists.size() - 1)); 
     for (List<String> list: partial) { 
      for (String s: lists.get(lists.size() - 1)) { 
       List<String> listCopy = new ArrayList<String>(list); 
       listCopy.add(s); 
       result.add(listCopy); 
      } 
     } 
     return result; 
    } 


    public static void main(String[] args) { 
     System.out.println(product(
       Arrays.asList(
         Arrays.asList("a1", "a2"), 
         Arrays.asList("b1", "b2", "b3"), 
         Arrays.asList("c1", "c2"), 
         Arrays.asList("d1", "d2")))); 
    } 
} 

Rant:これはPythonで非常に簡単です。またはRuby。 :)このような

+0

ありがとう、あなたは今日の私のヒーローです! – Mark

+0

あなたは正しいです。これはPythonでは簡単です。次のAndroidはPythonでなければなりません...愚かな時代遅れのJava ... – Radu

1

何かが動作するはずです(擬似コードとして扱う):Google Guava

List<List<int>> result = new List<List<int>>(); 
int[] indices = new int[number_of_lists]; 
for(int i = 0; i < indices.size(); i++) 
    indices[i] = 0; 

while(indices[0] < lists[0].size()) 
{ 
    List<int> temp = new List<int>(); 
    for(int i = 0; i < indices.size(); i++) 
    temp.add(lists[i].get(indices[i])); 
    result.add(temp); 

    indices[indices.size() - 1] += 1; 
    int i = indices.size(); 
    while(i >= 1 && indices[i] == lists[i].size()) 
    { 
    indices[i] = 0; 
    indices[i-1] += 1; 
    i--; 
    } 
} 
+0

私は実際に上記のような作業用コードに似ていました。 –

0

設定し、少なくともあなたの例の場合のために、something similar to what you wantを行うようです。ただし、結果リストをタプル形式にキャストする必要があります。これらはセットであり、リストではありませんが、あなたの例には少なくとも重複したエントリーがありませんので、おそらくこれが役に立ちます。

関連する問題