.net 如何避免类和方法的可访问性不一致的编译错误?

.net 如何避免类和方法的可访问性不一致的编译错误?,.net,public,access-modifiers,internals,.net,Public,Access Modifiers,Internals,我对Autodesk部件进行了反思,发现以下内容: 请注意,对于PressureNetwork类,它是public,并且有一个方法AddLinePipe,它也是public。但是,AddLinePipe,PressurePartSize的参数之一是internal 通常,我们无法在.Net中使用这样的代码进行编译(并且我们会得到“不一致的可访问性”之类的编译错误)。但不知怎的,这个集会侥幸逃脱了 我已经检查过了,组件中只有一个PressurePartSize 我不太确定什么时候有人说这件事做

我对Autodesk部件进行了反思,发现以下内容:

请注意,对于
PressureNetwork
类,它是
public
,并且有一个方法
AddLinePipe
,它也是
public
。但是,
AddLinePipe
PressurePartSize
的参数之一是
internal

通常,我们无法在.Net中使用这样的代码进行编译(并且我们会得到“不一致的可访问性”之类的编译错误)。但不知怎的,这个集会侥幸逃脱了

我已经检查过了,组件中只有一个
PressurePartSize

我不太确定什么时候有人说这件事做不到Autodesk已经这样做了;我参加了集会

不仅如此,人们还可以以某种方式使用C#中的库

将显示Autodesk.Civil.DatabaseServices.Styles.PressurePartSize 由于保护级别的原因,无法访问的错误


怎么做?我愿意使用任何语言来实现这一点,而不仅仅是C。或者.Net只是一个建议。可以有两个
PressurePartSize
类:公共类和内部类。从照片上看不清楚

大概是这样的:

namespace SampleLib
{
    using SampleLib.Internal;
    //using SampleLib.Public;

    public class PublicClass
    {
        public unsafe void PublicMethod(InternalClass internalClass) { }
    }
}

namespace SampleLib.Internal
{
    internal sealed class InternalClass { }
}

namespace SampleLib.Public
{
    public sealed class InternalClass { }
}
错误CS0051可访问性不一致:参数类型“InternalClass”的可访问性不如方法“PublicClass.PublicMethod(InternalClass)”的可访问性

但是

没问题。

更新

只有一个PressurePartSize,请参阅更新的问题

一开始,他们似乎拥有
Autodesk.Civil.DatabaseServices.Styles.PressurePartSize
public。然后,他们用
公共不安全对象AddLinePipe(LineSegment3d line,PressurePartSize partSize)
创建了一个库并构建了它。然后,他们将Autodesk.Civil.DatabaseServices.Styles.PressurePartSize更改为内部,但没有重建调用库。但JIT编译器在运行时检查可访问性。这就是问题的原因。

这不能在C#中完成。不过.NET虚拟机比C#更为宽松。有许多C#不公开的特性

在IL级别,您可以调用非公共方法。您还可以使用反射发射来生成运行时代码。这对于创建快速序列化程序非常有用

JIT还能够编译无法验证甚至不正确的IL。结果没有完全定义

这个程序集是如何创建的?我的第一个想法是,这是一个IL链接器工具的结果。NET程序集可以进行后处理以合并或优化它们。这也可能是混淆工具(尤其是无法反编译的方法)的结果

看起来该工具有一个bug,因为它肯定无意创建一个通常不可调用的公共方法


如果你想用它做实验,你可以将任何程序集反编译成IL,编辑并编译它。我相信任何东西都可以往返。

我不知道。但很少有人认为这个库是用C语言编写的。该库的开发人员可以使用不同的语言,使用不同的编译器,对这些东西要求不那么严格。(或者它可能是很久以前用C语言编写的,使用的是一个古老的C语言编译器,它还没有那种可访问性检查;我真的不知道,我只是边做边写这些东西。;-)你做不到。时期另一个问题是反编译的代码是什么意思,如果这两种PressurePartSize类型相同,它们是如何实现的,但在今天的C#编译器中,您无法做到这一点。值得注意的是,
PressureItemEnetwork
的唯一构造函数是内部的。我还质疑这种反编译的有效性,看起来Telerik反编译程序对这段代码进行了全面的反编译,您甚至确定它被正确地反编译了吗?这些部分是可读的吗?当然,它呕吐的原因当然可能是代码不是有效的C#,并且它试图将其硬塞进C#语法失败。这不是C#代码,它是用C++/CLI编写的。压力大小可能是一个本地C++类。C++/CLI编译器为此类发出元数据定义,但该类不可访问。只要调用是从C++/CLI代码进行的,就没有问题。这个反编译器在它上面死掉并不是非常罕见的。Reflector在这类代码上做得更好,但没有.NET反编译器会反编译本机代码。只有一个
PressurePartSize
,请参阅更新的问题
namespace SampleLib
{
    //using SampleLib.Internal;
    using SampleLib.Public;

    public class PublicClass
    {
        public unsafe void PublicMethod(InternalClass internalClass) { }
    }
}

namespace SampleLib.Internal
{
    internal sealed class InternalClass { }
}

namespace SampleLib.Public
{
    public sealed class InternalClass { }
}