字符串转枚举类型

5

在下面给出的声明中,是否有一种方法可以从字符串值(例如'one')检索枚举值(例如jt_one)?

type
 TJOBTYPEENUM =(jt_one, jt_two, jt_three);


CONST JOBTYPEStrings : ARRAY [jt_one..jt_three] OF STRING =
     ('one','two','three');

我需要创建一个嵌套的if语句集合来编写自己的函数吗?

注意:我不是在寻找字符串"jt_one"


5
这些全大写的标识符很难阅读,是我自己的问题还是普遍存在的?按照 Delphi 的规范应该这样写:TJobType = (jtOne, jtTwo, jtThree); - Andreas Rejbrand
1
抱歉,但我不确定每个人都完全遵循惯例,特别是我们这些刚开始学习的新手。也许你可以留出一些理解的空间? - Blow ThemUp
1
我不记得对你很粗鲁。但基于文本的沟通可能有点棘手,有时候人们会觉得某个人很粗鲁,而实际上他并不是。 - Andreas Rejbrand
2
@Jake,我可以向你保证,Andreas并没有失礼。他从来都不会。我们在这里往往会比较简洁,没有面对面交流时你所使用的礼貌用语。他只是建议使用帕斯卡命名法,即WhichLooksLikeThis,这样更容易阅读,并且更符合Delphi代码的标准。 - David Heffernan
@JakeSnake 我建议你阅读这篇文章:http://www.cs.ut.ee/~jellen/delphi/cs.html 它对于编写更整洁的 Pascal 标准代码非常有用,我发现它真的很有帮助。就像你一开始学习时一样,我也没有遵循任何标准,只是按照自己的方式编写代码。如果我现在看我的旧代码,我会感到震惊!从长远来看,使用通用标准会更有帮助,特别是在发布代码片段时,这使得每个人都更容易阅读。 - user1175743
Object Pascal 风格的标准参考在这里:http://edn.embarcadero.com/article/10280 - David Heffernan
2个回答

10
function EnumFromString(const str: string): TJOBTYPEENUM;
begin
  for Result := low(Result) to high(Result) do 
    if JOBTYPEStrings[Result]=str then
      exit;
  raise Exception.CreateFmt('Enum %s not found', [str]);
end;

实际代码中,您应该使用自己的异常类。如果您想允许不区分大小写的匹配,请使用SameText比较字符串。


@FabricioAraujo 这是一个相当著名的习语。我认为这基本上是线性搜索的规范Delphi实现。 - David Heffernan
1
我只是觉得很好奇,因为我倾向于像Andreas的示例一样编写代码。查看文档,这是完全有效的 - 因为循环被“Exit”语句中断(如果循环完成,则“Result”的值未定义)。 - Fabricio Araujo

7
function GetJobType(const S: string): TJOBTYPEENUM;
var
  i: integer;
begin
  for i := ord(low(TJOBTYPEENUM)) to ord(high(TJOBTYPEENUM)) do
    if JOBTYPEStrings[TJOBTYPEENUM(i)] = S then
      Exit(TJOBTYPEENUM(i));
  raise Exception.CreateFmt('Invalid job type: %s', [S]);
end;

或者,更整洁,
function GetJobType(const S: string): TJOBTYPEENUM;
var
  i: TJOBTYPEENUM;
begin
  for i := low(TJOBTYPEENUM) to high(TJOBTYPEENUM) do
    if JOBTYPEStrings[i] = S then
      Exit(i);
  raise Exception.CreateFmt('Invalid job type: %s', [S]);
end;

如果S不在数组中,该函数无法设置返回值。 - David Heffernan
这样更好。第一个版本使用强制转换很差。我建议你坚持使用第二个版本,把带有强制转换的那个删掉。 - David Heffernan
@David:是的,我意识到了。 - Andreas Rejbrand

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接