泛型或只是使用重载?

时间:2011-11-24 12:29:39

标签: c# oop class generics overloading

我有3个类,都有相似的属性。所有3个类中的3个属性的名称完全相同。相反,写3个方法(每个类一个)是否有某些方法我可以在这里使用泛型?

public static String GetAString(ActivityMedia activityMedia)
{
   return activityMedia.name;
}

public static String GetAString(AuditMedia auditMedia)
{
   return auditMedia.name;
}

public static String GetAString(VehicleMedia vehicleMedia)
{
   return vehicleMedia.name;
}

编辑:显然是为了简单地将这3种类型之一的对象传递给GetAString()

10 个答案:

答案 0 :(得分:4)

  1. 介绍具有单个string Name属性的接口
  2. 按接口
  3. 标记所有三个类
  4. 现在你可以直接评估媒体名称我不知道为什么你需要一个方法,但无论如何,你可以为界面类型IMedia
  5. 创建扩展方法
    interface IMedia
    {
        string Name { get; }
    }
    
    class ActivityMedia : IMedia
    class AuditMedia : IMedia
    class VehicleMedia : IMedia
    
    static class MediaExtensions
    {
       public static string GetName(this IMedia instance)
       {
              return instance.Name;
       }
    }
    

答案 1 :(得分:3)

如果它们完全不相关,则可以选择使用dynamic(如果您使用的是C#4):

public static String GetAString(dynamic d){
    return d.name;
}

编辑:

如果您不使用C#4.0,则可以使用反射:

public static string GetAString(object o)
{
    System.Reflection.PropertyInfo name = o.GetType().GetProperty("name");
    return (string) name.GetValue(o, null);
} 

答案 2 :(得分:3)

另一种选择是使用界面...

public interface INameable
{
   String Name { get; }
}

public static String GetAString(INameable nameable)
{
   return nameable.Name;
}

虽然此时您可能甚至不需要GetAString方法?

答案 3 :(得分:3)

您可以使用界面

执行此操作
public interface INamedMedia
{
    string Name { get; }
}

然后您的方法变为

public static String GetAString(INamedMedia media)
{
    return media.Name;
}

您的课程实施INamedMedia

public class Media : INamedMedia
{
    public string Name { get { return "Media"; } }
}

答案 4 :(得分:3)

我原本认为界面是理想的解决方案:

public interface IMedia
{
    public String Name { get; }
}

然后你可以让你的静态方法将该接口类型作为它的参数:

    public static String GetAString(IMedia media)
    {
        return media.Name;
    }

或者您的所有媒体类都可以从包含所需属性的基类型派生,并将其传递给方法而不是接口。

很难告诉你哪个是更好的选择,因为它已经取决于应用程序和继承链的复杂性。

article可能有所帮助

答案 5 :(得分:2)

你不需要泛型,你需要OOP和继承。

ActivityMediaAuditMediaVehicleMedia全部实现IMedia之类的基本界面或派生基本类MediaBase

然后只编写方法GetAString一次,接受IMedia对象或MediaBase对象。

另一个选项可能是您覆盖ToStringActivityMediaAuditMedia中的默认VehicleMedia方法,因此只需返回name属性,您只需调用{{ 1}}无需任何ToString方法。

答案 6 :(得分:2)

如果这些类没有共同的祖先,泛型将不会帮助你。解决方案是通过声明具有name属性的接口来安排它们共享共同的祖先。让每个类实现该接口,然后您就可以拥有一个GetAString函数。

答案 7 :(得分:2)

如果这三个类具有相同属性的子集,则最好使用基类中声明的公共属性和方法来实现基类,这些属性和方法是从三个媒体类派生而来的。

public class ActivityMedia : Media 
{

}

public class Media
{
     public string Name {get;set;}
}

这样,这三个类在一个地方定义了一组方法,使代码更容易维护。同时为您提供了将类特定方法放在其派生实现中的灵活性。

答案 8 :(得分:2)

在这里实现继承而不是泛型更合乎逻辑。

您也可以使用Interface,但这会使您的NameActivityMediaAuditMedia类的VehicleMedia属性重复。

考虑基类Media

public class Media
{
    // consider all properties that are common
    // on Media domain
    public string Name { get; set }
}

并从ActivityMedia班级继承AuditMediaVehicleMediaMedia

public class ActivityMedia : Media
{
    // other properties on ActivityMedia domain
}

public class AuditMedia : Media
{
    // other properties on AuditMedia domain
}

public class VehicleMedia : Media
{
    // other properties on VehicleMedia domain
}

现在在Media方法

上使用GetAString课程
public static String GetAString(Media activityMedia)
{
   return activityMedia.name;
}

public static String GetAString(Media auditMedia)
{
   return auditMedia.name;
}

public static String GetAString(Media vehicleMedia)
{
   return vehicleMedia.name;
}

答案 9 :(得分:1)

这是继承拯救的地方。有这样的基类:

public class Media
{
    public string name { get { return "Media"; } }
}

然后每个类将继承并定义自己的名称:

public class ActivityMedia : Media
{
    public new string name { get { return "Activity Media"; } }
}

最后:

public static String GetAString(Media media)
{
    return media.name;
}

编辑:因为你坚持使用当前的设计,你可以使用反射:

public static String GetAString(object media)
{
    PropertyInfo propName = media.GetType().GetProperty("name");
    if (propName != null)
        return propName.GetValue(media, null);
    return "";
}