3

現在、MMORPG のボットを作成しています。ただし、現在、これをうまく実装する方法を見つけようとしているところです。設計上の問題は、キャラクターの呪文を正しい順序で唱えることに関連しています。これは、アーカイブする必要があるものの簡単な例です。それらをキャストすることとは関係ありませんが、正しい順序で実行します。どのスキルがまだキャストされていないかを確認することで、それらをランダムにキャストする方法を簡単に知ることができますが、実際にはGUIに表示されているように正しい順序ではありません。

注: スキル量は異なる場合があり、必ずしも 3 ではなく、最大 10 です。

Charactername < foobar > は 3 つのスキルを持っています。

スキル 1: 名前 (ランダム 1) クールダウン (1000 ミリ秒) 詠唱時間 (500 ミリ秒)

スキル 2: 名前 (ランダム 2) クールダウン (1500 ミリ秒) キャスト持続時間 (700 ミリ秒)

スキル 3: 名前 (ランダム 3) クールダウン (2000 ミリ秒) キャスト持続時間 (900 ミリ秒)

これをどのように実装できるかはよくわかりません。誰か考えがある場合は、お気軽に共有してください。ほとんどの人がゲームで不正行為をするという考えが好きではないことは知っています.

ありがとうございました。

4

5 に答える 5

3

これは、より「インテリジェントなエージェント」の領域に進出しています。AI 用の計画データベースを用意することを検討してください。cast-fireball-spell プランには、ignite-fire スペルの前提条件があり、それ自体が create-gas-bubble スペルのケーシングの成功の前提条件になっている場合があります。計画を選択するには、すべての前提条件を満たす必要があるため、AI が気泡を作成できるが、気泡に点火できない場合、計画は失敗し、別のことを行う必要があります (おそらく再試行します)。

于 2009-08-25T06:10:01.607 に答える
2

たぶん、あるイベントハンドラーから、どの呪文を唱えるかを決めたいと思うでしょう。おそらく、このスペルキャスターのようなものから始めることができます:

public class Caster
{
    private readonly ICastable[] _spells;
    private int _canCastAt;

    public Caster(ICastable[] spells)
    {
        _spells = spells;
        _canCastAt = -1;
    }

    public string GetNextSpellToCast(int currentTime)
    {
        if (currentTime < _canCastAt)
            return null;

        for (int i = 0; i < _spells.Length; i++)
        {
            int durationOfCast = _spells[i].AttemptCast(currentTime);

            if (durationOfCast > 0)
            {
                _canCastAt = currentTime + durationOfCast;
                return _spells[i].GetName();
            }
        }

        return null;
    }
}

術者は呪文を唱えます:

public interface ICastable
{
    string GetName();
    int AttemptCast(int msCurrentTime);
}

あなたは特定の種類の呪文について説明しました:

public class ChanneledSpell : ICastable
{
    private readonly string _name;
    private readonly int _castDuration;
    private readonly int _castCooldown;
    private int _lastCast;

    public ChanneledSpell(string name, int castDuration, int castCooldown)
    {
        Debug.Assert(castDuration < castCooldown);  // a reasonable assumption the tests makes

        _name = name;
        _castDuration = castDuration;
        _castCooldown = castCooldown;
        _lastCast = -_castCooldown;
    }

    public string GetName()
    {
        return _name;
    }

    public int AttemptCast(int msCurrentTime)
    {
        if (msCurrentTime > _lastCast + _castCooldown)
        {
            _lastCast = msCurrentTime;
            return _castDuration;
        }

        return 0;
    }
}

これはC++とマークされているようですが、この答えはC#ですが、C ++で使用可能な言語構造のみを使用したため、簡単な翻訳である必要があります。私がそれほど簡単に翻訳できなかったのは、いくつかのテストです。

[TestFixture]
public class SpellTest
{
    [Test]
    public void TestCanCastOnStartup()
    {
        var sut = new ChanneledSpell(Some.String(), Some.PositiveNonzeroInteger(), Some.PositiveNonzeroInteger());

        int result = sut.AttemptCast(Some.PositiveNonzeroInteger());

        Assert.IsTrue(CastWasMade(result));
    }

    [Test]
    public void TestCantCastUntilCooldown()
    {
        int firstCast = Some.PositiveNonzeroInteger();
        int duration = Some.PositiveNonzeroInteger();
        int cooldown = duration + Some.PositiveNonzeroInteger();  // assuming spell duration is less then cooldown

        var sut = new ChanneledSpell(Some.String(), duration, cooldown);

        int ignored = sut.AttemptCast(firstCast);
        int secondCastAttempt = sut.AttemptCast(firstCast + cooldown - 1);
        int thirdCastAttempt = sut.AttemptCast(firstCast + cooldown + 1);

        Assert.IsFalse(CastWasMade(secondCastAttempt));
        Assert.IsTrue(CastWasMade(thirdCastAttempt));
    }

    [Test]
    public void TestReportsTimeOnCast()
    {
        int duration = Some.PositiveNonzeroInteger();
        int firstCastTime = Some.PositiveNonzeroInteger();

        var sut = new ChanneledSpell(Some.String(), duration, Some.PositiveNonzeroInteger());

        int firstCastAttempt = sut.AttemptCast(firstCastTime);

        Assert.AreEqual(duration, firstCastAttempt);
    }

    private bool CastWasMade(int result)
    {
        return result > 0;
    }
}
于 2009-08-25T07:14:01.370 に答える
0

私が見た中で最も高度なボットであるOpenKoreボットを見てください。これは大きなオープンソース プロジェクトであり、数年前から存在し、多くのボット AI 固有の問題が解決されました。そこからいくつかのアイデアを得る/学ぶことができると思います。しかし、OpenKoreはほとんど Perl で書かれています。

于 2009-09-18T07:23:01.437 に答える