2013-10-08 185 views
2

我枚举原始的Java代码:替换字符串与枚举枚举生成自动protobuf的

public enum CarModel { 
    NOMODEL("NOMODEL"); 
    X("X"), 
    XS("XS"), 
    XSI("XS-I"); //NOTE the special - character. Can't be declared XS-I 
    XSI2("XS-I.2"); //NOTE the special . character. Can't be declared XS-I.2 
    private final String carModel; 
    CarModel(String carModel) { 
     this.carModel = carModel; 
    } 

    public String getCarModel() { return carModel; } 

    public static CarModel fromString(String text) { 
     if (text != null) { 
      for (CarModel c : CarModel.values()) { 
       if (text.equals(c.carModel)) { 
        return c; 
       } 
      } 
     } 
     return NOMODEL; //default 
    } 
} 

现在,如果我使用protobuf的,我得到的.proto文件:

enum CarModel { 
    NOMODEL = 0; 
    X = 1; 
    XS = 2; 
    XSI = 3; 
    XSI2 = 4; 
} 

从我earlier question我知道我可以调用由protoc生成的枚举并删除我自己的类(从而避免重复的值定义),但我仍然需要定义某处(在包装类?包装枚举类?)备用fromString()方法将返回正确的字符串每枚枚举。我怎么做?

编辑: 如何实现如下:

String carModel = CarModel.XSI.toString(); 这将返回 “XS-I”

和:

CarModel carModel = CarModel.fromString("XS-I.2"); 

回答

4

您可以使用Protobuf的"custom options"完成此操作。

import "google/protobuf/descriptor.proto"; 

option java_outer_classname = "MyProto"; 
// By default, the "outer classname" is based on the proto file name. 
// I'm declaring it explicitly here because I use it in the example 
// code below. Note that even if you use the java_multiple_files 
// option, you will need to use the outer classname in order to 
// reference the extension since it is not declared in a class. 

extend google.protobuf.EnumValueOptions { 
    optional string car_name = 50000; 
    // Be sure to read the docs about choosing the number here. 
} 

enum CarModel { 
    NOMODEL = 0 [(car_name) = "NOMODEL"]; 
    X = 1 [(car_name) = "X"]; 
    XS = 2 [(car_name) = "XS"]; 
    XSI = 3 [(car_name) = "XS-I"]; 
    XSI2 = 4 [(car_name) = "XS-I.2"]; 
} 

现在在Java中,你可以这样做:

String name = 
    CarModel.XSI.getValueDescriptor() 
    .getOptions().getExtension(MyProto.carName); 
assert name.equals("XS-I"); 

https://developers.google.com/protocol-buffers/docs/proto#options(略微向下滚动到自定义选项的部分。)

+0

我试过你的代码,看起来protoc不会创建getProto()方法,我需要调用它才能将ValueDescriptor转换为Extension。有任何想法吗 ? –

+0

还有一件事 - 当查看生成的java代码时,“XS-I”和“XS-I.2”字符串出现的唯一位置在最后一个字段中,该字段定义为:“static {java.lang.String [] descriptorData = {“基本上保存了我的.proto源码 –

+0

糟糕,对不起,该方法被称为'toProto',而不是'getProto'。我会编辑我的答案。 是的,注释都进入descriptorData。我给出的代码实际上将它们从那里提取出来。 –

-1
CarModel carmodel = Enum.valueOf(CarModel.class, "XS") 

CarModel carmodel = CarModel.valueOf("XS"); 
+0

我需要另一个方向:弦模型= CarModel.XSI。的toString();但能够告诉它XSI转换为“XS-I”。还有以下CarModel carModel = CarModel.fromString(“XS-I”); –