前提・実現したいこと
C#で、Listの全要素の積集合を求めたいのですが、やり方が分かりません。
LinqにIntersectというメソッドがありますが、これは2つのListを比較するものです。
1つのListに含まれる全要素を対象にしたいのですが、foreachなどを使っても上手く求められません。
該当のソースコード
C#
1[Flags] 2public enum UnitElement { 3 Blue = (1 << 0), 4 Red = (1 << 1), 5 Male = (1 << 2), 6 Female = (1 << 3), 7 Human = (1 << 4), 8 Robot = (1 << 5), 9 Naked = (1 << 6), // 裸眼 10 Glass = (1 << 7), // 眼鏡 11 AllZero = 0b00000000, 12 AllOne = 0b11111111, 13} 14 15public clas Unit{ 16 public Element element; 17} 18 19public class Union { 20 public List<Unit> list = new List<Unit> (); 21 public Union () { } 22 public Union (List<Unit> unitList) { list = unitList; } 23 24 /// <summary> 25 /// 全てのUnit属性の論理積を返す。 26 /// </summary> 27 /// <returns>共通属性がない・1つしかUnitがない場合はAllZeroを返す</returns> 28 public UnitElement AndElement () { 29 UnitElement flag = UnitElement.AllZero; 30 if (IsEmpty () || list.Count == 1) return flag; 31 foreach (var unit in list) { 32 flag = flag == UnitElement.AllZero ? 33 unit.Element : unit.Element & flag; 34 } 35 return flag; 36 }
こんな感じです。Union.AndElement()を実行することで、Union.listにいる全Unitの共通属性を取得したいのです。
foreachで1つずつ抽出する場合、記憶するための変数(flag)へどう代入するかが悩みです。
Enum型はnullを許容しないので、初期値用のUnitElement.Allzeroを代入させてからforeachを回すのですが、
AllZeroは全てが0なので、単純に&で比較すると必ず0になってしまいます。
よって、AllZeroの場合は初期値とみなしてlistの要素をそのまま代入させてみましたが、
そうすると今までに比較した段階で0だった場合と区別ができません。
例)unit01とunit02に共通属性が1つもないままunit03と比較した場合
試したこと
論理積を求める記事を調べると、大抵は比較数分の変数を定義して&演算子で比較しています。
C#
1Unit unit01 = new Unit(); 2Unit unit02 = new Unit(); 3unit01.element = UnitElement.Blue | UnitElement | Male | UnitElement.Robot; 4unit02.element = UnitElement.Blue | UnitElement | Male | UnitElement.Human; 5UnitElement flag = unit01.element & unit02.element; // Blue, Male
このunit01や02が何人になった時でも対応できるようにlistの全要素で比較対象にしたいです。
回答3件
あなたの回答
tips
プレビュー
バッドをするには、ログインかつ
こちらの条件を満たす必要があります。
2019/03/05 14:30