Наследуется только внутри сборки в С#

В С# Есть ли способ указать класс, который должен быть унаследован только классом, присутствующим в той же сборке, и для других сборок должен вести себя как открытый закрытый тип.

Ответ 2

У самого языка нет ничего, что бы облегчило это, но вы должны это сделать, создав внутренние конструкторы. Однако, если вы это сделаете, вы не сможете обновить его из внешних сборок, поэтому вам придется добавить метод factory.

public class Foo
{
    internal Foo()
    {
    }

    public Foo Create()
    {
        return new Foo();
    }
}

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

public sealed class Foo : FooBase
{

}

public class FooBase
{
    internal FooBase() { }
}

Однако, один вопрос, который вы можете задать себе, - это именно то, почему вы хотите, чтобы класс был запечатан. Иногда это неизбежно, но я видел, что ключевое слово sealed так часто злоупотребляли, что я думал, что я его подниму. Часто разработчики запечатывают классы, потому что они чрезмерно защищают свой код. В большинстве случаев, если класс хорошо разработан, его не нужно закрывать.

Ответ 3

Если ваш класс является абстрактным, существует очень простой способ сделать это:

public abstract class Foo {
    internal abstract void DoNothing();
    // ... other members
}

Теперь, хотя ваш класс и большинство членов являются общедоступными, внутренний абстрактный член делает невозможным вывод из класса вне вашей сборки.

Ответ 4

Вы не можете сделать это с помощью языковых конструкций, но попробуйте с отражением

public class MyClass{
  public MyClass(){
    if(this.GetType().Assembly != typeof(MyClass).Assembly){
        throw new Exception("Can't derive from this type!");
  }
}

Проверено. Кажется, работает. Единственная проблема заключается в том, что, если кто-то не читает документацию, проблема известна во время выполнения.

Ответ 5

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

public interface IFoo
{
}

internal class Foo : IFoo
{
}

public sealed class PublicFoo : IFoo
{
    private Foo m_Foo = new Foo();
}

Ответ 6

Я знаю, что это старый пост, но я нашел другой способ, который работает очень хорошо, и я хотел опубликовать его для других людей.

  • Сделать базовый класс с внутренним конструктором.
  • Сделайте производные классы наследуемыми от базового класса и запечатайте.

`` ``

public abstract class LockResult {
    internal LockResult() {

    }
}

public sealed class LockSucceededResult : LockResult {
    //Info for when a lock succeeded
}

public sealed class LockFailedResult : LockResult {
    //Info for when a lock failed
}

`` ``

Ответ 7

Нет. На языке С# этого не существует. Однако обходные пути - как это предлагают другие участники - могут быть достаточными.