Java中字符串转换的简单属性

时间:2008-12-15 23:00:58

标签: java string encoding

使用Java,我需要编码Map< String,String>名称值对存储到String中,并能够再次解码它。这些将存储在数据库列中,并且通常可能简短,因此常见的情况应该产生一个简单漂亮的行,但不应该破坏数据,即使它包含意外的字符等。

你会如何选择这样做:

  • 编码的表格是单一的,人类易读的行
  • 它不需要大型库或很多上下文来编码/解码
  • 任何分隔符都已正确转义

网址编码? JSON?自己做?请指定您使用的任何帮助程序库或方法。

(根据要求编辑以指定更多上下文和要求。)

7 个答案:

答案 0 :(得分:5)

正如@Uri所说,额外的背景会很好。我认为您的主要关注点不在于特定的编码方案,因为对于简单的Map<String, String>来说,为大多数编码滚动自己很简单。

一个有趣的问题是:这个中间字符串编码将用于什么?

  • 如果它纯粹是内部的,那么ad-hoc格式很好,例如简单连接:

    key1|value1|key2|value2
    
  • 如果人类晚上读它,像Ruby的地图声明这样的格式很不错:

    { first_key  => first_value, 
      second_key => second_value }
    
  • 如果编码是通过网络将序列化地图发送到另一个应用程序,那么XML建议很有意义,因为它是标准的,并且合理地自我记录,代价是XML的冗长。

    <map>
        <entry key='foo' value='bar'/>
        <entry key='this' value='that'/>
    </map>
    
  • 如果要将地图刷新到文件并稍后由另一个Java应用程序回读,@ Cletus对Properties class的建议是一个很好的建议,并且具有易于使用的额外好处开放并由人类检查。


编辑:您已添加了要存储在数据库列中的信息 - 是否有理由使用单个列,而不是像这样使用三列:

CREATE TABLE StringMaps 
(
    map_id NUMBER   NOT NULL,  -- ditch this if you only store one map...
    key    VARCHAR2 NOT NULL,
    value  VARCHAR2
);

除了让您存储更多具有语义意义的数据外,这还可以更正式地将编码/解码移动到您的数据访问层,并允许其他数据库读取器轻松查看数据,而无需了解您可能使用的任何自定义编码方案。如果您愿意,也可以通过键或值轻松查询。


再次编辑:你说它确实需要适合单个列,在这种情况下我要么:

  • 使用第一个以管道分隔的编码(或者您喜欢的任何外来字符,也许是一些不可打印的英文unicode字符)。最简单的事情。或...

  • 如果您使用像Oracle这样的数据库将XML识别为真实类型(因此可以对其进行XPath评估等等)并且需要能够从数据库层中很好地读取数据,使用XML。编写用于解码的XML解析器永远不会有趣,但使用这样一个简单的模式不应该太痛苦。

即使您的数据库本身不支持XML,您也可以将其放入任何旧的类似字符的列类型...

答案 1 :(得分:3)

为什么不使用Properties class?这正是你想要的。

答案 2 :(得分:1)

我一直在考虑通过外观模式为我的客户端和服务器之间的对话(传输内容)选择公共表示的类似需求。我想要一个标准化,人类可读(简短),健壮,快速的表示。我希望它实现和运行轻量级,易于测试,并且易于“包装”。请注意,我已经通过我的定义和明确的意图消除了XML。

通过“wrap”,我的意思是我想支持其他传输内容表示,例如XML,SOAP,可能是Java属性或Windows INI格式,逗号分隔值(CSV)等,Google协议缓冲区,自定义二进制格式,专有二进制格式,如Microsoft Excel工作簿,以及可能出现的任何其他格式。我将使用主要外观周围的包装器/装饰器来实现这些辅助表示。这些次要表示中的每一个都是可取的,特别是在某些情况下与其他系统集成,但由于各种缺点(未能满足上面列出的一个或多个标准),它们都不适合作为主要表示。

因此,到目前为止,我选择将JSON格式作为主要的传输内容表示。我打算在不久的将来详细探讨这个选项。

仅在极端性能考虑的情况下,我才会跳过翻译基础传统格式。清洁设计的优点包括良好的性能(无需浪费精​​力,易于维护),适当的硬件选择应该是唯一必要的补充。当性能需求变得极端时(例如,每天处理四万个传入数据文件,总计四万次交易),无论如何都必须重新审视所有内容。

作为开发人员,DBA,架构师等,我构建了几乎所有尺寸和描述的系统。我对自己选择的标准充满信心,并急切地等待确认其适用性。实际上,我希望将一个实现发布为开源(但不要屏住呼吸)。

请注意,此设计讨论忽略了有意的传输介质(HTTP,SMTP,RMI,.Net Remoting等)。我发现将传输介质和传输内容视为完全独立的设计考虑因素,彼此之间以及与所讨论的系统相比更为有效。实际上,我的目的是使这些实际上“可插拔”。

因此,我鼓励您强烈考虑JSON。祝福。

答案 3 :(得分:0)

该问题的一些额外背景会有所帮助。

如果要以整个地图粒度进行编码和解码,为什么不使用XML?

答案 4 :(得分:0)

正如@DanVinton所说,如果你需要内部使用(我的意思是“

  

内部使用

as

  

它仅由我的组件使用,而不是由其他人编写的组件

你可以连接键和值。 我更喜欢在键和键之间使用不同的分隔符和键和值:
而不是 key1+SEPARATOR+value1+SEPARATOR+key2 etc
我代码
key1+SEPARATOR_KEY_AND_VALUE+value1+SEPARATOR_KEY(n)_AND_KEY(N+1)+key2 etc

如果你必须调试,这种方式更清晰(按设计也是如此)

答案 5 :(得分:0)

查看apache commons配置包。这将允许您以XML或属性格式读取/保存文件。它还为您提供了自动将属性更改保存到文件的选项。

Apache Configuration

答案 6 :(得分:0)

意识到这是一个古老的“致命”线索,但我有一个以前没有提出的解决方案,我认为值得投入戒指。

我们在标准XML属性格式的DB中的单个features列中存储地理CLOB的“任意”属性(即由用户在运行时创建)。那就是:

name="value" name="value" name="value"

要创建XML元素,只需在xml元素中“包装”属性即可。那就是:

String xmlString += "<arbitraryAttributes" + arbitraryAttributesString + " />"

将一个属性实例“序列化”到一个xml-attributes-string是一个简单的...它就像十行代码。我们很幸运,因为我们可以向用户强加所有属性名称必须是有效的xml-element-names的规则;我们xml-escape(即“e; etc)”每个“值”以避免双引号和值字符串中的任何问题。

它有效,灵活,快速(足够)和简单

现在,说了这么多......如果我们有时间,我们只是通过存储完整的未掺杂的未解释的元数据xml文档完全脱离整个“元数据问题”在CLOB中使用其中一个开源元数据编辑器来处理整个混乱。

干杯。基思。