Java 列表识别与解析算法
我的数据理论上是一个列表,但从历史上看,它是由用户作为一个自由格式的文本字段输入的。现在,我需要将列表中的每个项目分开,以便可以分析每个元素 用户输入的我的数据的简化示例:Java 列表识别与解析算法,java,python,list,parsing,Java,Python,List,Parsing,我的数据理论上是一个列表,但从历史上看,它是由用户作为一个自由格式的文本字段输入的。现在,我需要将列表中的每个项目分开,以便可以分析每个元素 用户输入的我的数据的简化示例: one, two, three, four, five one. two. three, four. five. "I start with one, then do two, maybe three and four then five" one two three four five. on
one, two, three, four, five
one. two. three, four. five.
"I start with one, then do two, maybe three and four then five"
one
two
three
four
five.
one, two. three four five
one two three four - five
"not even a list, no list-elements here! but list item separators may appear. grrr"
所以,这或多或少就是数据的样子。实际上,一个列表项可能有好几个单词长。我需要处理这些列表(其中有数千个),以便最终得到如下数组:
array[0] = "one"
array[1] = "two"
array[n] = n
我承认有时我的算法会完全无法解析列表,我不需要100%的成功率,75%就好了。误报对我来说是非常昂贵的,所以我宁愿完全拒绝一个列表,也不愿生成一个不包含真实数据的列表——假设一些用户输入了无意义的胡言乱语
我有一些想法,可以尝试确定使用了哪些分隔符,以及与内容大小相关的数据分隔规则
我更喜欢Java或Python,但是任何解决方案都是受欢迎的:-)在Java中,字符串标记器将实现这一点(即StringTokenizer(inputString,delimiterList)) 印刷品 A B C D以下命令将把输入字符串“解析”为由非单词字符分隔的“单词”字符序列
String input = ...
String[] parts = input.split("[^\w]*");
我不知道你怎么区分一张清单和胡言乱语。我想你需要进一步解释你的问题领域
编辑:如果你不能定义你(作为一个人)用来区分列表和胡言乱语的规则,那么这个问题基本上是无法解决的。你知道,计算机不会变魔术
也许你应该用这个程序来处理那些“绝对”列表的子集,然后手工对其他的列表进行分类。我不知道我是否理解你的问题。如果您想从python中混乱的字符串中提取字母数字字符串,那么应该是:
>>> import re
>>> re.split('\W+','abaa, asodf ?. poasid - paosfi sec')
['abaa', 'asodf', 'poasid', 'paosfi', 'sec']
或者,如果您知道分隔符:
>>> re.split('[,. -]+','abaa, asodf, poasid - paosfi sec')
['abaa', 'asodf', 'poasid', 'paosfi', 'sec']
如果你不能定义你的数据(“单词可以是任何东西,我无法事先知道任何单个列表可以包含什么。它们不仅仅是数字……它可能是任何东西的列表”),那么你就有严重的问题 具体来说,如果您不能定义数据,您的问题就无法解决 你可以试着玩 你可以丢弃“噪音词”(“,”,“,”,“,”我“,”开始“,”用“,”然后“,”做“,”等等),剩下的可能是这个不可定义的“词可以是剩下的任何东西”
除非你能更好地定义你的数据,否则你可能注定要经历很多挣扎。解决这个问题的第一步是详细分析人类是如何解决这个问题的。我将把这个问题分成两部分
最后,我假设当前数据不仅被人类输入和识别,而且被人类消费。您将项目分解为列表的原因是为了将人从循环中移除,还是为了让他们的工作更轻松?如果是后者,我建议为他们提供分解列表元素,并作为备份,提供最初输入的文本。换言之,如果你做错了,就要对冲赌注。要么你知道你的单词词典,要么你有列表分隔符的优先顺序。否则,这个问题的定义太模糊,计算机无法处理 我想你的优先顺序可以是逗号,点,连字符,空格。因此,这意味着您可以使用逗号进行拆分,而不是使用点等进行拆分
或者,您可以继续按每个连续的分隔符进行拆分,直到找到文本中不存在的分隔符。我不确定最佳答案到底是什么,但如果您需要很少的误报,那么您可能应该定义一些很可能是列表的模式,并严格拒绝所有其他数据
patterns = [
re.compile(r'^\s*(\w+)(\s*,\s*(\w+))*\s*$'),
re.compile(r'^\s*(\w+)(\s*\.\s*(\w+))*\s*$'),
re.compile(r'^\s*(\w+)(\s*,\s*(\w+))*\s+and\s+(\w+)\s*^$')
]
acceptSet = [ line for line in candidateSet if
any(pattern.match(line) for pattern in patterns)]
与其关注代码,不如关注方法。根据斯威尔登说的做一点准备 如果您的列表被人类用户使用,您可以要求他们在您出错时纠正您(此纠正对输入文本的用户或稍后查看文本的用户可见)。如果一个给定的输入看起来很像一个列表,但还不足以确定,你可以向他们显示列表和原始输入,并让他们选择 要将输入自动分类为列表或文本,您可以创建多个度量标准,以便根据这些标准做出决策:
- 给定分隔符(即
),该短语使用多少个分隔符?期待一两个。哪一个[“”、\t'、“、”、“、”、“、”和“]
- 是由片段组成的输入(使用某种语法系统)-片段倾向于表示列表
- 此输入字段(或输入中的上下文)是否倾向于包含列表项
- 列表中的单词本身(有些单词可能总是表示您所在领域中的一个句子或列表)
patterns = [
re.compile(r'^\s*(\w+)(\s*,\s*(\w+))*\s*$'),
re.compile(r'^\s*(\w+)(\s*\.\s*(\w+))*\s*$'),
re.compile(r'^\s*(\w+)(\s*,\s*(\w+))*\s+and\s+(\w+)\s*^$')
]
acceptSet = [ line for line in candidateSet if
any(pattern.match(line) for pattern in patterns)]
rawdata = """\
one, two, three, four, five
one. two. three, four. five.
"I start with one, then do two, maybe three and four then five"
one
two
three
four
five.
one, two. three four five
one two three four - five
"not even a list, no list-elements here! but list item separators may appear. grrr"
a dog with a bone is a beautiful twosome""".splitlines()
from pyparsing import oneOf, WordStart, CharsNotIn, alphas, LineEnd
options = (WordStart() + oneOf("one two three four five") + (CharsNotIn(alphas)|LineEnd()))
for userinput in rawdata:
print userinput
print [opt[0] for opt in options.searchString(userinput)]
print
one, two, three, four, five
['one', 'two', 'three', 'four', 'five']
one. two. three, four. five.
['one', 'two', 'three', 'four', 'five']
"I start with one, then do two, maybe three and four then five"
['one', 'two', 'three', 'four', 'five']
one
['one']
two
['two']
three
['three']
four
['four']
five.
['five']
one, two. three four five
['one', 'two', 'three', 'four', 'five']
one two three four - five
['one', 'two', 'three', 'four', 'five']
"not even a list, no list-elements here! but list item separators may appear. grrr"
[]
a dog with a bone is a beautiful twosome
[]