Как я могу наследовать строковый класс? - PullRequest
19 голосов
/ 05 декабря 2011

Я хочу наследовать, чтобы расширить класс строки C # для добавления методов, таких как WordCount() и нескольких других, но я продолжаю получать эту ошибку:

Ошибка 1 'WindowsFormsApplication2.myString': невозможно получитьиз запечатанного типа 'string'

Есть ли какой-нибудь другой способ, которым я могу обойти это?Я пробовал с string и String, но это не сработало.

Ответы [ 7 ]

65 голосов
/ 07 апреля 2014

Другим вариантом может быть использование неявного оператора.

Пример:

class Foo {
    readonly string _value;
    public Foo(string value) {
        this._value = value;
    }
    public static implicit operator string(Foo d) {
        return d._value;
    }
    public static implicit operator Foo(string d) {
        return new Foo(d);
    }
}

Класс Foo действует как строка.

class Example {
    public void Test() {
        Foo test = "test";
        Do(test);
    }
    public void Do(string something) { }
}
36 голосов
/ 05 декабря 2011

System.String запечатан, поэтому нет, вы не можете этого сделать.

Вы можете создать методы расширения . Например,

public static class MyStringExtensions
{
    public static int WordCount(this string inputString) { ... }
}

использование:

string someString = "Two Words";
int numberOfWords = someString.WordCount();
11 голосов
/ 18 августа 2014

Если вы намерены наследовать от строкового класса просто создать псевдоним для строкового класса , поэтому ваш код более самоописан, тогда вы не можете наследовать от строки.Вместо этого используйте что-то вроде этого:

using DictKey = System.String;
using DictValue= System.String;
using MetaData = System.String;
using SecurityString = System.String;

Это означает, что ваш код теперь более самоописан, а намерение более ясное, например:

Tuple<DictKey, DictValue, MetaData, SecurityString> moreDescriptive;

На мой взгляд, этот кодпоказывает большее намерение по сравнению с тем же кодом, без псевдонимов:

Tuple<string, string, string, string> lessDescriptive;

Этот метод алиасинга для большего самоописания кода также применим к словарям, хэш-наборам и т. д.

Конечно, если вы хотите добавить функциональность к классу строк, то лучше всего использовать методы расширения.

4 голосов
/ 05 декабря 2011

Вы не можете получить из строки, но вы можете добавить расширения, такие как:

public static class StringExtensions
{
    public static int WordCount(this string str)
    {
    }
}
2 голосов
/ 05 декабря 2011

Что не так с классом помощника? Как говорится в вашем сообщении об ошибке, строка запечатана , поэтому ваш текущий подход не будет работать. Методы расширения - ваш друг:

myString.WordCount();


static class StringEx
{
    public static int WordCount(this string s)
    {
        //implementation.
    }
}
1 голос
/ 05 декабря 2011

Вы не можете наследовать запечатанный класс (в этом весь смысл), и причина, по которой он не будет работать как с string, так и с System.String, заключается в том, что ключевое слово string является просто псевдонимом для System.String.

Если вам не нужен доступ к внутренним объектам строкового класса, вы можете создать Extension Method, в вашем случае:

//note that extension methods can only be declared in a static class
static public class StringExtension {

    static public  int WordCount(this string other){
        //count the word here
        return YOUR_WORD_COUNT;
    }

}

У вас по-прежнему не будет доступа к закрытым методам и свойствам строкового класса, но IMO это лучше, чем писать:

StringHelper.WordCount(yourString);

Так же работает LINQ.

0 голосов
/ 05 декабря 2011

Строковый класс помечен sealed , потому что вы не должны наследовать от него .

Так что нет, вы не можете "обойти это".

То, что вы можете сделать, это реализовать эти функции в другом месте.Либо как простые статические методы в каком-либо другом классе, либо как методы расширения , позволяющие им выглядеть как строковые члены.

Но вы не можете "обойти"это когда класс помечен как запечатанный.

...