1

他の Java プロジェクトで使用する Java ライブラリを作成しています。プロジェクトはRepast Symphonyを使用しており、私のライブラリも使用しています (したがって、このエラーは何らかの競合が原因であると思います)。すべてが正常にビルドされますが、Repast シミュレーションを実行するとスローされますjava.lang.NoClassDefFoundError: repast/simphony/context/Context

ライブラリをjarとしてエクスポートし、プロジェクトを直接インポートして、ライブラリをプロジェクトのクラスパスに追加しようとしましたが、役に立ちませんでした。私は何が間違っている可能性がありますか?

この Context クラスは、ライブラリとプロジェクトの両方で使用されています。以下は、2 つのクラスでの使用のスニペットです。

// MyContextBulder.java
// This file is in my project
// This class is called by Repast first
import repast.simphony.context.Context;
import repast.simphony.dataLoader.ContextBuilder;
import mylibrary.core.DF;
import mylibrary.core.DF.MyContext;

public class MyContextBuilder implements ContextBuilder<Object> {

    @Override
    public Context<Object> build(Context<Object> context) {

        context.setId("test");
        DF.setContext((MyContext) context);

        // Create agent
        new MyAgent();
        // Add the agent to the Repast context.
        // context.add(t);

        return context;
    }
}
// DF.java
// This file is in my library

import java.util.Collection;
import java.util.HashMap;
import java.util.Iterator;

import org.apache.commons.collections15.Predicate;

import repast.simphony.context.Context;
import repast.simphony.context.ContextListener;
import repast.simphony.space.projection.Projection;
import repast.simphony.util.collections.IndexedIterable;
import repast.simphony.valueLayer.ValueLayer;
import mylibrary.Agent;


/**
 * This static class provides the Directory Facilitator Service
 * and is used to send messages to agents
 * and to keep a directory of all agents in the application.
 * Agents use the static method send(ACLMessage) to send a message
 * to one or more agents. The ACLMessage object contains
 * the receiver agent and the sender (so the receiver can reply back).
 * 
 * This class needs to be setup initially before registering new agents.
 * To do that, simply call setContext(...);
 * @author joaolopes
 *
 */
public class DF {

    private static int lastAID = 0; // Just to help generate new identifiers
    private static HashMap<Integer, Agent> agents; // Contains all agents

    /**
     * The Repast context that contains all
     * scheduled Repast objects.
     */
    private static MyContext context = null;

    /**
     * Registers the agent in the directory and returns its
     * AID (freshly generated for it). If the agent is already
     * registered, returns its current AID.
     * @param agent The agent to be registered
     * @return The AID generated for the agent.
     */
    public static int registerAgent(Agent agent) {
        // If this agent is already in the hashMap,
        // just return its key.
        if (getAgents().containsValue(agent)) {
            return agent.getAID();
        }

        // Quick way to find a new ID for this agent
        // that is not in use at the moment.
        while (getAgents().containsKey(lastAID)) {
            lastAID++;
        }

        // The agent must know their own ID.
        agent.setAID(lastAID);
        agents.put(lastAID, agent);
        System.err.println(context.toString());
        context.add(agent);
        return lastAID;
    }

    public static void setContext(MyContext c){
        context = c;
    }
}

コメントから関連情報を追加するための編集: ライブラリで行っているように、repast JAR をプロジェクトに直接インポートしません。Repast Symphony はプラグインとして Eclipse にインストールされているので、すべての Repast ライブラリを含む「Repast Projects」を作成しました。したがって、クラスの競合の原因となっている特定の JAR を削除できません。

4

2 に答える 2

2

まさにあなたが言ったように。このエラーは、jar 内の同じクラス間の競合である必要があります。IDE を使用している場合は、ビルドをクリーンアップして再ビルドしてみてください。

また、symphony ライブラリ jar を 1 つだけ使用することをお勧めします。複数のクラス定義は、常に JVM クラス ローダーのあいまいさにつながります。

インポートするプロジェクトでは symphony jar を使用しないようにしてください。これは、エクスポートした jar に既にあるためです。ライブラリをインポートした後、エラーは発生しません。

これを試して、どうなるか教えてください。

ビルドツールを使用することをお勧めします。Mavenのようなもの。次に、適切なプラグインを使用した Maven がこの問題を解決します。必要な作業は、特定の jar ファイルが必要であることを Maven に伝えることだけです。その後、魔法が発生し、配布する jar ファイルが適切に機能します。

于 2014-03-31T17:14:00.670 に答える