你写的最好(最有用)的界面是什么?

时间:2008-11-30 16:23:17

标签: c# interface

标题基本上是拼出来的。您编写了哪些界面让您感到自豪并且您使用了很多。我想那些写IEnumerable<T>而不是IQueryable<T>的人在创作后感觉很好。

6 个答案:

答案 0 :(得分:5)

严格的界面?或者只是一个API?我很高兴generic operator的内容如何解决(可用here) - 我定期看到有人询问有关使用泛型的运算符,所以我很高兴它是对很多人来说都是一个方便的答案。它可能是slightly easier in C# 4.0,但我非常怀疑它会如此快 - DLR树/动态内容有一个开销。

我也很高兴在Jon已经提到的推送LINQ中有所帮助;-p

答案 1 :(得分:3)

我对Push LINQ核心界面的设计感到满意。这是一个非常简单的界面,但有了它,你可以做各种有趣的事情。这是定义(从内存来看,但它至少会非常接近):

public interface IDataProducer<T>
{
    event Action<T> DataProduced;
    event Action EndOfData;
}

基本上它允许观察者“监听”数据流,而不是以IEnumerable的工作方式“拉”出来。

三个兴趣点:

  • 这个名字很糟糕。我想重命名它,我有一些很好的反馈,但是 名称还没有。
  • 事件处理程序不遵循具有发送方/事件args的标准.NET约定。在这种情况下,这样做真的没有多大意义。
  • 事件的多播性质使其非常适合计算多个聚合等。所有这些都是免费的。

答案 2 :(得分:1)

  

我猜那些编写IEnumerable的人......在创建[it]后感觉很好。

我不太确定。接口变得IEnumerable非常失败。事实上,IEnumerable<T>,它的通用对应物,实际上提供了一个完全不同的接口。 (好吧,“不同”并不是一个好词;基本上,它增加了可处置性并且不再强调完全无用的Reset方法;但是,这种方法当然仍然存在。)

此外,具有相似结构的类似语言(Java会浮现在脑海中)具有更好,更可扩展的构造,以满足相同的需求(以及更多)。例如,Java的迭代器可以扩展为双向或允许修改访问(而IEnumerable始终是只读的。)

编辑:由于评论中存在如此多的争议,请让我澄清一下。我不是说IEnumerable(或IEnumerator接口。他们是足够的。但是,他们本可以做得更好。如果没有别的,那么至少Reset方法看起来就像混乱。

Terjet说他“一直都在使用它” - 这正是我的观点! IEnumerable是整个.NET框架的关键接口。它无处不在。没有它就没有.NET。因此,要求完美的界面是否太过分了?

“充足”只是失败的另一个词。

答案 3 :(得分:1)

为了进行MVP模式工作,我有一些基本的框架接口:

public interface IValidatable {
  bool IsValid { get; set; }
  void ShowValidationFailureMessage(string message);
}

public interface ISubmitable {
  event EventHandler Submit;
  void ShowSubmitFailureMessage(string message);
  void ShowSubmitSuccessMessage(string message);
}

public interface ICancelable {
  event EventHandler Cancel;
}

通过这3个接口,我可以编写具有这些通用操作的演示者(基本上涵盖所有表单操作)。例如:

public interface ILogin : IValidatable, ISubmitable, ICancelable {
  string Username { get; set; }
  string Password { get; set; }
}

然后,您可以创建一个演示者并将其存根。

答案 4 :(得分:0)

我正在研究一个验证系统,我计划尽快向社区发布。它本质上是Specification模式的实现。

核心界面本质上是功能性的:

public interface ICheckable<T>
{
    CheckResult Apply(T target);
}

CheckResult是表示三态值的structPassedFailedIgnored。所有转换和运算符重载都已到位,将其视为Boolean值。

这允许验证者表达“我没有意见”,而不是返回误导性的true值(想想RangeValidator表示空字段有效,因此它与RequiredFieldValidator一起使用)。

组合很自然,并且使用静态类来完成。检查中的每个点都是下一个操作的隐式And

public static ICheckable<T> Add<T>(this ICheckable<T> check, ICheckable<T> otherCheck)
{
    return new Check<T>(t => check.Apply(t) && otherCheck.Apply(t));
}

public static ICheckable<T> Either<T>(this ICheckable<T> check, ICheckable<T> firstCheck, ICheckable<T> secondCheck)
{
    return check.Add(t => firstCheck.Apply(t) || secondCheck.Apply(t));
}

public static ICheckable<T> Not<T>(this ICheckable<T> check, ICheckable<T> negatedCheck)
{
    return check.Add(t => !negatedCheck.Apply(t));
}

扩展方法很有效:

public static ICheckable<int> Percentage(this ICheckable<int> check)
{
    return check.Add(n => n >= 0 && n <= 100);
}

public static ICheckable<T> GreaterThanOrEqualTo<T>(this ICheckable<T> check, T value) where T : IComparable<T>
{
    return check.Add(t => t.CompareTo(value) >= 0);
}

public static ICheckable<T> LessThanOrEqualTo<T>(this ICheckable<T> check, T value) where T : IComparable<T>
{
    return check.Add(t => t.CompareTo(value) <= 0);
}

public static ICheckable<T> Range<T>(this ICheckable<T> check, T minimum, T maximum) where T : IComparable<T>
{
    return check.GreaterThanOrEqualTo(minimum).LessThanOrEqualTo(maximum);
}

// RangeExcludeMinimum
// RangeExcludeMaximum
// RangeExclusive

每个操作都包含重载,这些重载需要检查构建lambda:

public static ICheckable<T> Add<T>(this ICheckable<T> check, Func<ICheckable<T>, ICheckable<T>> makeCheck)
{
    return check.Add(makeCheck(new IgnoredCheck<T>()));
}

所以你可以这样做语法:

ICheckable<int> check;

check.Add(i => i.Percentage().GreaterThan(50).Even());

答案 5 :(得分:0)

这是一个ActionScript 3界面,它是我们用于Flash Player在as3中的新行为的核心。

public interface IDisposable {
  public function dispose():void;
}

正如您所期望的那样,dispose方法应该关闭所有资源并删除任何可能的引用。

C ++程序员可能会嘲笑这个“创新”界面(这是完全公平的),但as3引入了很多围绕Flash内存管理的问题。对于许多编译语言来说,这些问题都是“老套”,但是动作脚本程序员现在才第一次遇到这些挑战。

是的,它仍然是一种垃圾收集语言。但无论好坏,与ActionScript 2相比,“手持”的数量要少得多,这需要这个界面。