6

私はこのようなエンティティの最初のリストを持っています:

public partial class Networking :EntityBase
{

    public virtual int NetWorkingId
    {
        get;
        set;
    }

    public virtual string NetWorkingParam
    {
        get;
        set;
    }

    public virtual System.DateTime NetWorkingDate
    {
        get;
        set;
    }
}

そして、次のようなエンティティの 2 つ目のリストがあります。

public partial class PrivateNetwork :EntityBase
{
    public virtual int PrivateNetworkId
    {
        get;
        set;
    }

    public virtual int ContaId
    {
        get { return _contaId; }
        set
        {
            if (_contaId != value)
            {
                if (Contact != null && Contact.ContaId != value)
                {
                    Contact = null;
                }
                _contaId = value;
            }
        }
    }

    public virtual Nullable<System.DateTime> DateCreation
    {
        get;
        set;
    }
}

これら 2 つのリストを 1 つにまとめて、すべての要素を日付順に並べ替えたいと思います。

それは可能ですか?

4

6 に答える 6

6

あまりきれいではありませんが、これを行うことができます。最終的には、IEnumerable<object>使用する前に各アイテムのタイプを確認する必要があります。

IEnumerable<object> sorted = myNetworkingList
    .Concat<object>(myPrivateNetworkList)
    .OrderBy(n => n is Networking
                 ? (DateTime?)((Networking)n).NetWorkingDate
                 : ((PrivateNetwork)n).DateCreation);

foreach (object either in sorted)
{
    if (either is Networking)
        // Networking; do something
    else
        // PrivateNetwork; do something else
}
于 2012-11-13T08:22:57.450 に答える
5

この問題は、ポリモーフィズムを使用することで簡単に解決できます。DateTime並べ替えたいプロパティを持つ、両方のクラスに共通の基本クラスまたはインターフェイスを使用します。

例:

public abstract class NetworkingBase : EntityBase
{
    public DateTime DateToSortOn { get; set; }
}

また

public interface INetworking
{
    public DateTime DateToSortOn { get; set; }
}

そして、クラスを次から派生NetworkingBaseまたは実装しINetworkingます。

public partial class Networking : NetworkingBase
{
    ...
}

public partial class PrivateNetwork : NetworkingBase
{
    ...
}

また

public partial class Networking : EntityBase, INetworking
{
    ...
}

public partial class PrivateNetwork : EntityBase, INetworking
{
    ...
}

結果のコレクションに対してLINQ UnionorConcatを実行し、次に を実行します。OrderBy

于 2012-11-13T08:20:58.410 に答える
2

私が以前に尋ねるべきだったのはです。。。

並べ替えたらどうしますか?

これに対する答えは、潜在的なソリューションに大きな影響を与える可能性があります。

答えが「日付のリストを表示する必要がある」のようなものである場合は、日付のみを順番に表示する必要があります。その場合、2つのリストをマージする必要はありません。順序付けられた日付だけのシーケンスを取得し、それを使用できます。

var orderedDates = networks.Select(n => n.NetworkingDate)
                   .Union(privateNetworks.Select(n => n.DateCreation))
                   .OrderBy(date => date);

答えが、オブジェクトのIDにリンクする日付を示すリンクのリストと、オブジェクトのタイプを識別するための何かを表示する必要がある場合は、匿名オブジェクトを使用して、上記のようなものを回避できます。

var orderedDates = networks.Select(n => new {Date = n.NetworkingDate, Id = n.NetWorkingId, NetworkType = n.GetType().Name})
                   .Union(privateNetworks.Select(n => new {Date = n.DateCreation, Id = n.PrivateNetWorkingId, NetworkType = n.GetType().Name}))
                   .OrderBy(n => n.Date);

ただし、答えが最も古い10個のネットワークにShutdown()コマンドを送信する必要がある場合は、メソッドを呼び出すことができる単一のタイプがあり、特定のメソッドに解決されるポリモーフィックソリューションが本当に必要です。使用しているタイプ。Shutdown()Shutdown()

ユーザーkhellangの答えがうまくいかない場合にのみ使用するポリモーフィックソリューション

別の回答へのコメントから

@BinaryWorrierデータベースにすでにレコードがあるため、この回答を選択しました。新しいインターフェイスを追加する場合、インターフェイスを追加する前に、すでに保存されているレコードをどのように処理しますか?

ORMでインターフェイスをエンティティクラスに追加できず、そのインターフェイスやそのメンバーにマークを付けてORMで無視されないようにすることは、信じがたいことです。

ただし、新しいインターフェイスまたは基本クラスを追加できない場合でも、これを多態的に行うことができます。

インターフェイスを追加し、ネットワーククラス(Abstractorクラス)ごとにインターフェイスを実装するクラスを追加してから、ネットワーククラスをクラスに変換し、Abstractorそれらをに追加して、List<INetwork>そのリストを並べ替えます。

public interface INetwork
{
    DateTime? Date { get; }
}

public class PrivateNetworkAbstractor
    :INetwork
{
    private PrivateNetwork network;
    public PrivateNetworkAbstractor(PrivateNetwork network)
    {
        this.network = network;
    }
    public DateTime? Date
    {
        get { return network.DateCreation; }
    }
}

public class NetworkingAbstractor
    : INetwork
{
    private Networking networking;
    public NetworkingAbstractor(Networking networking)
    {
        this.networking = networking;
    }
    public DateTime? Date
    {
        get { return networking.NetWorkingDate; }
    }
}
...

public IEnumerable<INetwork> MergenSort(IEnumerable<Networking> generalNetWorks, IEnumerable<PrivateNetwork> privateNetWorks)
{
    return generalNetWorks.Select(n => new NetworkingAbstractor(n)).Cast<INetwork>()
    .Union(privateNetWorks.Select(n => new PrivateNetworkAbstractor(n)).Cast<INetwork>())
    .OrderBy(n=> n.Date);
}
于 2012-11-13T14:38:53.707 に答える
1

日付を持つインターフェイスを作成し、両方のクラスに実装します。その後の並べ替えは簡単です。

public interface INetwork
{
    DateTime? Date { get; }
}

public partial class Networking :EntityBase, INetwork
{
    public DateTime? Date
    {
        get { return NetWorkingDate; }
    }
}

public partial class PrivateNetwork :EntityBase, INetwork
{
    public DateTime? Date
    {
        get { return DateCreation; }
    }
}

var commonList = new List<INetwork>();
// Add instances of PrivateNetwork and Networking to the list

var orderedByDate = commonList.OrderBy(n => n.Date);
于 2012-11-13T08:23:53.800 に答える
0

最初の解決策は匿名タイプを使用することです

using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;

namespace Example1
{
    class Program
    {
        class Human
        {
            public string Name { get; set; }
            public string Hobby { get; set; }
            public DateTime DateOfBirth { get; set; }
        }
        class Animal
        {
            public string Name { get; set; }
            public string FavouriteFood { get; set; }
            public DateTime DateOfBirth { get; set; }
        }

        static void Main(string[] args)
        {
            var humans = new List<Human>
            {
                new Human
                {
                    Name = "Kate",
                    Hobby = "Fitness",
                    DateOfBirth = DateTime.Now.AddYears(-27),
                },
                new Human
                {
                    Name = "John",
                    Hobby = "Cars",
                    DateOfBirth = DateTime.Now.AddYears(-32),
                },
            };

            var animals = new List<Animal>
            {
                new Animal
                {
                    Name = "Fluffy",
                    FavouriteFood = "Grain",
                    DateOfBirth = DateTime.Now.AddYears(-2),
                },
                new Animal
                {
                    Name = "Bongo",
                    FavouriteFood = "Beef",
                    DateOfBirth = DateTime.Now.AddYears(-6),
                },
            };

            var customCollection = (from human in humans
                                    select new
                                        {
                                            Name = human.Name,
                                            Date = human.DateOfBirth,
                                        }
                                        ).Union(from animal in animals
                                                select new
                                                    {
                                                        Name = animal.Name,
                                                        Date = animal.DateOfBirth,
                                                    }).OrderBy(x => x.Date);


            foreach (dynamic customItem in customCollection)
                Console.WriteLine(String.Format("Date: {0}, Name: {1}",      customItem.Date, customItem.Name));

            Console.Read();
        }
    }
}

または匿名タイプなし(作成されたCustomClass):

...
class CustomClass
        {
            public string Name { get; set; }
            public DateTime Date { get; set; }
        }
...
var customCollection = (from human in humans
                                    select new CustomClass
                                        {
                                            Name = human.Name,
                                            Date = human.DateOfBirth,
                                        }
                                        ).Union(from animal in animals
                                                select new CustomClass
                                                    {
                                                        Name = animal.Name,
                                                        Date = animal.DateOfBirth,
                                                    }).OrderBy(x => x.Date);


            foreach (CustomClass customItem in customCollection)
                Console.WriteLine(String.Format("Date: {0}, Name: {1}", customItem.Date, customItem.Name));

...
于 2012-11-14T19:14:28.883 に答える