0

有两个项目,一个在 C++ CLI 中,另一个在 C# 中。我的 C# 项目中引用了 C++ CLI 程序集

我在 C++ CLI 中有这个类:

public class ref Player{
    private:
    int id_;
    public:
    Player(int Id) : id_(Id){}
}

在这个项目的其他部分,我定义了一组允许的玩家。

在 C# 中,我希望只能访问数组并保护程序员Player在 C# 中创建另一个类实例。

代码中的虚构:
在 C# 中我想要:

PlayersArray[0].dostuff();

在 C# 中我不想要:

Player x = new Player(1);
x.dostuff();
4

5 回答 5

4

一种方法是为要公开的功能定义一个接口Player,然后实现该接口,现在不要Player公开。

这迫使消费者只能Player通过接口进行交互,当然,您不能构造接口。

于 2013-03-12T07:33:20.293 回答
2

将构造函数设为私有?在 C++ 中,还可以将复制构造函数设为私有...

于 2013-03-12T07:31:57.880 回答
2

要使其在 C++ 而非 C# 中可实例化,请将构造函数internal设置为 C++/CLI 程序集:

internal:
    Player(int Id) : id_(Id) {}

这使得构造函数仅对定义它的程序集可见,因此您可以在 C++/CLI 程序集中但不能在外部构造对象。

为了使它可以被Player类之外的任何东西实例化,请创建构造函数private

private:
    Player(int Id) : id_(Id) {}
于 2013-03-12T07:32:20.980 回答
0

最简单的方法是将 Player 的构造函数标记为私有,并从 Player 类内部创建和填充 PlayersArray

于 2013-03-12T07:32:47.900 回答
0

您想控制对象的创建,这对于工厂模式来说是一项完美的工作!

您可以创建一个包含这些值的集合,将构造函数设为私有并创建一个包含全局玩家数据的静态变量:

public class Player
{
    // For access
    public static IEnumerable<Player> Players { get; private set; }

    public int Id { get; private set; }

    // Private constructor
    private Player(int Id)
    {
        this.Id = Id;
    }

    // Factory method
    public static void CreatePlayers(int NumPlayers)
    {
        // Only create players collection once!
        if (Players != null)
            throw new InvalidOperationException();

        Players = new List<Player>(NumPlayers);

        for (int i = 0; i < NumPlayers; i++)
        {
            var player = new Player(i);
            player.Players = Players;
            Players.Add(player);
        }
    }

    public void DoStuff()
    {
        // ...
    }
}

即使这是 C#,也应该很容易将其转换为 CLI/C++。确保您还将复制构造函数声明为私有。其他答案也提到了internal访问器,但我个人试图阻止使用,internal因为它打破了传统的 OOP 设计。

于 2013-03-12T07:40:02.290 回答