0

.java Filesカバーターとして機能するutil-classを作成しています-ジェネレーター。

このutil-classはAConverter.java'を生成します(以下のサンプルを参照)。util-classの

記述方法を知りたいです。
私はグーグルで検索し、apachebcelを使用することをお勧めします。.java Fileしかし、からを記述Stringしてプログラムで機能させる例を見つけることができませんでした。



期待は...

class ADTO
{
    private String empId;
    private String empName;
    private String dept;

    //setters and getters
}

class ABO
{
    private String loginId;
    private String userName;
    private String group;

    //setter and getter
}

class AConverter
{
    public void doConvertFromDB(ADTO source, ABO dest)
    {
        dest.setLoginId(source.getEmpId());
        ...
    }

    public void doConvertFromBO(ABO source, ADTO dest)
    {
        dest.setEmpId(source.getLoginId());
        ...

    public ADTO getSourceClass()
    {
        return ADTO.class;
    }

    public ABO getDestClass()
    {
        return ABO.class;
    }
}

上記のクラスAConverterは、新しいUtilクラスによって生成されます。

4

2 に答える 2

4

これを別の方法で行おうとすると、ほぼ確実に利益が得られます。このスキームが失敗する可能性のある方法の数は、心配なほど多くあります。以下にいくつかの提案を示します。

  1. 何らかのキャスター メソッドを追加します。

    class ADTO
    {
        private String empId;
        private String empName;
        private String dept;
    
        // setters and getters
    
        public ABO toABO() // caster method (ABO will need a toADTO() as well)
        {
            ABO a = new ABO();
    
            a.setSomething(getSomethingEquivalent());
            ...
    
            return a;
        }
    }
    
  2. プロキシ クラス。意図したクラスのサブクラスである可能性があります。各クラスから派生した 2 つが必要です。

    class ADTO_Proxy extends ADTO
    {
        private ABO abo;
    
        public ADTO_Proxy(ABO a)
        {
            super();
            abo = a;
        }
    
        @override
        public String getEmployeeId()
        {
            return abo.getLoginId();
        }
    
        // other setters and getters
    }
    
  3. アダプターを作成しようとするのではなく、クラスをマージします。次の方法で簡単に実現できます。

    class ADTO
    {
        private String empId;
        private String empName;
        private String dept;
    
        // getters and setters for each variable by each name
        public String getEmployeeId()
        { return empId; }
        public String getLoginId()
        { return empId; }
    
        public String getEmployeeName()
        { return empName; }
        public String getUsername()
        { return empName; }
    
        public String getDepartment()
        { return dept; }
        public String getGroup()
        { return dept; }
    
        // setters
    }
    

    これは、インターフェイスでも実行できます。

HateYourselfLater™ 評価:

最初の方法は、3 つの中で最高の 2 にランク付けされます。誤って 2 つを切り替えることがなく、他のコードを変更する必要がほとんどないため、評価が得られます。

2 番目の方法では、3 つの中間の -3 にランク付けされます。あるタイプのオブジェクトを別のタイプのオブジェクトと混同することがあり、意図しない副作用が発生する可能性があるため、獲得した評価。プロキシ クラスからセッターを省略すると、これを評価 0 に減らすことができますが、これにより機能が制限されます。

3 番目の方法は、3 つの中で最悪の -5 を取得します。副作用の可能性が多く、冗長なコードが後でつまずく可能性があるため、評価を獲得しました。ただし、1 つのクラスのみを適切に使用するようにすべてをリファクタリングすることでレート 1 にすることはできますが、それには多くの作業が必要になる可能性があり、今では自分が嫌いになるでしょう。

とはいえ、オンザフライでクラスを生成して約-10の2つのランク間で変換するという最初のアイデアは、維持するのが恐ろしく難しく、基礎となるクラスの変更に非常に敏感であり、おそらく簡単に壊れるからです。

HateYourselfLater™ スケールの範囲は -10 から 10 で、10 が最大のいいね、-10 が最大のヘイトです。

元の回答:

逆コンパイラが必要です。選択できるJava逆コンパイラがいくつかあります。いくつかをリストします。

  • Showmycode - 使いやすく、まともな逆コンパイル、オンライン(したがって、企業の資料には不向き)、組み込みのクラス名とネストされた匿名クラスを台無しにする
  • Jad - ダウンロード可能、CLI、動作するが醜いコードが生成される、Linux バージョンが古くなっている (必要に応じて Windows バージョンと Wine を使用する)、enum を台無しにする、foreach ループ、およびいくつかの try/catch を使用する
  • Fernflower - CLI、見つけるのが難しい、3 つの中で最良の出力、著者は SO ユーザー、見栄えの良い出力、試行錯誤を時々失敗する

どれも完璧ではありませんが、それはコンパイル中に一部のデータが失われるという事実の結果であり、逆コンパイラはプログラムが元のように見えたものを推測する必要があります.

于 2012-08-01T15:11:34.860 に答える
0

複数のことができます。

何をしたいのかを正確に決定し、一致するライブラリを取得して、そのライブラリを学習する必要があります。

BCEL はそのようなライブラリの 1 つです。過去にJava-APTを同様の目的で使用して成功しました。

あなたの理解のために、クラスの生成について以下にいくつか書きますが、これを自分で開発しないでください。おそらく行き詰まるでしょう。

現在実行中の同じ JVM 内でクラスを使用できるようにする場合 (コードを生成し、プログラム全体を再度コンパイルして再起動するのとは対照的に)、次のことを行う必要があります。

  1. ファイルを作成し、文字列を書き込みます。
  2. ファイルをコンパイルします (これを行う大まかな方法​​は、コードから javac を呼び出すことです)
  3. クラスをクラスローダーにロードします。
于 2012-08-01T15:11:46.843 に答える