3

6 つの配列のデカルト積が必要です。問題は、いつでも最大 5 つの配列が null になる可能性があることです。すべての配列が取り込まれている場合はうまく機能しますが、配列のいずれかがnullの場合は爆撃します

私の配列はこのようなものです

MatrixArray_1[0] = 1
MatrixArray_1[1] = 2

MatrixArray_2[0] = null
MatrixArray_2[1] = null

MatrixArray_n[0] = 2
MatrixArray_n[1] = 2

私は現在このコードを使用しています... http://blogs.msdn.com/b/ericlippert/archive/2010/06/28/computing-a-cartesian-product-with-linq.aspxから派生したものです

var product1 =  from first in MatrixArray_1
                from second in MatrixArray_2
                from third in MatrixArray_3
                from fourth in MatrixArray_4
                from fifth in MatrixArray_5
                from sixth in MatrixArray_6
                select new[] { first, second, third, fourth, fifth, sixth };
            string[][] myCombos_linq = product1.ToArray();

私は入れようとしMatrixArray_n where first != nullましたが、それは最初のnull配列で停止し、残りのすべての配列を読み取らないため、配列1と配列3が入力されていても、戻り配列は常に0行です。

この時点で、コード/ロジックの変更は何でも歓迎されます! ティア

4

3 に答える 3

3

エリックのアプローチは を使用することであるため、次のIEnumerable<IEnumerable<T>>ようなことを行う必要があります。

エリックのコード:

static IEnumerable<IEnumerable<T>> CartesianProduct<T>(this IEnumerable<IEnumerable<T>> sequences) 
{ 
  IEnumerable<IEnumerable<T>> emptyProduct = new[] { Enumerable.Empty<T>() }; 
  return sequences.Aggregate( 
    emptyProduct, 
    (accumulator, sequence) => 
      from accseq in accumulator 
      from item in sequence 
      select accseq.Concat(new[] {item})); 
}

電話サイト:

var sequences = new int?[][] { MatrixArray_1, MatrixArray_2, ..., MatrixArray_6 };
var cartesianSequence = sequences.CartesianProduct();

呼び出しサイトを変更します。

var cartesianSequence = sequences.Where(a => a.Any(e => e != null)).CartesianProduct();

Where 呼び出しは、すべての要素が null であるシーケンスを除外します。

null 配列と null 値のみを含む配列を除外するには、次のようにします。

var cartesianSequence = sequences.Where(a => a != null && a.Any(e => e != null)).CartesianProduct();

または、クエリ内包表記を使用すると、次のようになります。

var filteredSequences = 
    from sequence in sequences
    where sequence != null && sequence.Any(e => e != null)
    select sequence
var cartesianSequence = filteredSequences.CartesianProduct();

編集

もう 1 つの可能性は、一部の要素が非 null であっても、各シーケンスの null 要素を除外することです。

var filteredSequences = 
    from sequence in sequences
    where sequence != null && sequence.Any(e => e != null)
    select (from v in sequence where v.HasValue select s)
var cartesianSequence = filteredSequences.CartesianProduct();

また

var cartesianSequence = sequences
    .Where(s => s != null && s.Any(e => e != null))
    .Select(s => s.Where(v => v != null))
    .CartesianProduct();

しかし、結果に対して何を行っているかがわからないため、何をアドバイスすればよいかを正確に知ることは困難です。

于 2012-02-14T17:23:28.733 に答える
1

firstsecondなどのいずれかが である場合、それらを除外したいということを正しく理解していますnullか? 簡単だ:

追加するだけ

select new [] { first, second, third, fourth, fifth, sixth }.Where(x => x != null)

あなたのクエリに。

firstまたは、second、 などのいずれかが である場合、六つ子全体を除外したいnullですか? それも簡単です。追加するだけ

where new [] { first, second, third, fourth, fifth, sixth }.All(x => x != null)

あなたのクエリに。let配列を 2 回作成しないように使用することもできます。

于 2012-02-14T17:26:16.673 に答える