简体   繁体   English

C#,WinForms和扩展方法

[英]C#, WinForms and Extension Methods

The Question 问题

Aside from all the obvious answers, what would cause extension methods to generate compiler errors like this one: 除了所有显而易见的答案之外,还会导致扩展方法生成此类编译器错误的原因:

'DataType' does not contain a definition for 'YourExtensionMethodName' “数据类型”不包含“ YourExtensionMethodName”的定义

I've got a real stumper here, and it's spelled out for you in detail below. 我这里有一个真正的树桩,下面为您详细说明。 I've exhausted all the possible causes I can think of. 我已经尽了所有我能想到的可能原因。

Scenario 脚本

  • I have a couple of extension methods defined in various static classes in a DLL that is consumed by a WinForms application. 我在WinForms应用程序使用的DLL中的各种静态类中定义了几个扩展方法。
  • The extension method signatures do not conflict with the signatures of methods on the class I'm extending ( String , in this case). 扩展方法签名与我要扩展的类(在这种情况下为String )上的方法签名不冲突。
  • Both the DLL and the WinForms application are written in C#. DLL和WinForms应用程序均使用C#编写。
  • Both the DLL and the WinForms application are configured to target .NET 3.5. DLL和WinForms应用程序都配置为以.NET 3.5为目标。
  • The consuming classes include a reference to the namespace that defines the extension method. 消费类包括对定义扩展方法的名称空间的引用。 Its spelling has been verified. 它的拼写已经过验证。
  • If I reference the extension class directly, the extension methods appear. 如果我直接引用扩展类,则会出现扩展方法。 For example, if I type StringExtensions. 例如,如果我键入StringExtensions. , Intellisense appears as normal, with all of my extension methods listed. ,Intellisense正常显示,列出了我的所有扩展方法。
  • EDIT : The errors are occurring in the WinForms application, but only for some of the extension methods, not all of them. 编辑 :这些错误是在WinForms应用程序中发生的,但仅适用于某些扩展方法,而不是全部。

The Code (Or an Excerpt Thereof) 代码(或其摘录)

(Yep, this is the offending code) (是的,这是有问题的代码)

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

namespace Roswell.Framework
{
    public static class StringBuilderExtensions
    {
        public static string ToSentenceCase(this string value)
        {
            return value.Substring(0, 1).ToUpper() + value.Substring(1).ToLower();
        }

        public static string ToTitleCase(this string value)
        {
            string[] parts = value.Split(new string[] {" "}, StringSplitOptions.None);
            System.Text.StringBuilder builder = new System.Text.StringBuilder();
            foreach (string part in parts)
            {

                builder.Append(part.ToSentenceCase());
                builder.Append(" ");
            }
            return builder.ToString();
        }

    }
}

And this is the code that consumes it: 这是消耗它的代码:

using Roswell.Framework;

namespace Roswell.Windows.Command
{
    /// <summary>
    /// Views the SQL for an object in the database window.
    /// </summary>
    internal class ViewObjectDdlCommand
        : MainWindowCommand
    {

        public override void Execute()
        {
           // ...

           OpenCodeWindow(
               string.Format("{0} - {1} - {2}", 
                             dsn.Name, 
                             objectName, 
                             info.ToTitleCase()),
                schemaItemType,
                objectName);
         }
    }
}

From your code snippet, I can see you're calling ToTitleCase on something called info . 从您的代码段中,我可以看到您正在调用名为info ToTitleCase But I can't see the type of that variable, which is the thing that will determine what is happening here. 但是我看不到该变量的类型,这将决定这里发生的事情。

Obviously it needs to be a string (if string was not a sealed class it could be something derived from string, but that's impossible for a sealed class). 显然,它必须是字符串(如果string不是密封类,则可能是从string派生的东西,但是对于密封类来说这是不可能的)。

So the only thing that makes sense (aside from a very unlikely compiler error) is that info is not a string. 因此,唯一有意义的(除了极不可能的编译器错误)是info不是字符串。

The error suggests the answer: 该错误提示了答案:

'DataType' does not contain a definition for 'YourExtensionMethodName' “数据类型”不包含“ YourExtensionMethodName”的定义

In this case, my guess is that "info" ( ViewObjectDdlCommand.info ) is not a string, but rather DataType. 在这种情况下,我的猜测是“ info”( ViewObjectDdlCommand.info )不是字符串,而是DataType。 Try changing it to: 尝试将其更改为:

OpenCodeWindow(
    string.Format("{0} - {1} - {2}", 
        dsn.Name, 
        objectName, 
        info.ToString().ToTitleCase()),
        schemaItemType,
        objectName);

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM