繁体   English   中英

将字符串转换为对象数组

[英]Convert a string into an array of objects

目前我有这个字符串:

"Hello, I'm <%first%> <%last%>, and I <3 being a <%occupation%>. I am > blah";

如何将它分成一个 object 数组,如下所示:

[
  { type: 'string', value: 'Hello, I'm ' },
  { type: 'token', value: 'first' },
  { type: 'string', value: ' ' },
  { type: 'token', value: 'last' },
  { type: 'string', value: ', and I <3 being a ' },
  { type: 'token', value: 'occupation' },
  {type: 'string', value: 'I am > blah'}
]

字符串的模式是,如果我们找到一个看起来像这样的单词:<%word%>,然后我们将它作为 object 类型放入数组中。 否则,我们将其作为类型字符串放入。 我的问题是我们如何在代码中实现它。

我很难形成将成为 key valuevalue的短语。 下面是我尝试实现的代码,但它是错误的。 我的想法是有一个单词变量,它是空的,当它通过字符串时,它会连接单词以形成阶段。 一旦它看到它在<%%>之间,它将被赋予一个类型token并推入arrStr数组。

但是有两个问题:1)似乎使用此代码,正在生成从“H”到“He”到“Hel”到“Hell”到“Hello”的字符串的每次迭代。 2)它似乎从不接触令牌。 3) "hello" 中的第一个 "h" 以某种方式被省略了。

如何在不使用正则表达式的情况下做到这一点?

var str = "Hello, I'm <%first%> <%last%>, and I <3 being a <%occupation%>. I am > blah";
var arr = str.split('<%');
var final = [], vala, thetype;
arr.forEach(val => {
 vala=val.split('%>');
 thetype='string';
 if (vala.length>0) thetype='token';
 final.push({type: thetype, value: vala[0]});
})

我确信正则表达式会是一个更好的解决方案,但我不知道。 所以这是我的方法:

 let txt = "Hello, I'm <%first%> <%last%>, and I <3 being a <%occupation%>. I am > blah"; var arr = []; txt.split("<%").forEach(x => { if (x.includes("%>")) { x.split("%>").forEach((y, i) => { arr.push({type: i == 0? 'token': 'string', value: y}); }) } else { arr.push({type: 'string', value: x}); } }); console.log(arr);

使用两次替换


让我们使用一些虚拟字符串替换 angular 括号以轻松拆分数据。

因此,我们将<%替换为*#%>仅替换为*

然后我们只用* split数据。 拆分后我们有以下数组

[
  "Hello, I'm ",
  "#first",
  " ",
  "#last",
  ", and I <3 being a ",
  "#occupation",
  ". I am > blah",
]

因此,我们仅在开始的 angular 括号中添加的额外#将帮助我们区分标记和字符串。

现在我们可以简单地 map 这个数组并得到想要的结果。

注意:您可以使用确定不会出现在字符串中的适当虚拟字符串。

 const str = "Hello, I'm <%first%> <%last%>, and I <3 being a <%occupation%>. I am > blah", res = str.replace(/<%/g, "*#").replace(/%>/g, "*").split("*").map((v) => v[0] === "#"? { type: "token", value: v.slice(1) }: { type: "string", value: v } ); console.log(res);

您可以使用这样的正则表达式解析字符串:

 const input = "Hello, I'm <%first%> <%last%>, and I <3 being a <%occupation%>. I am > blah"; const regex = /<%([^%]+)%>/g; let result; let parsed = []; let lastIndex = 0; while(result = regex.exec(input)) { const { 1: match, index } = result; parsed.push({ type: 'string', value: input.substring(lastIndex, index) }); parsed.push({ type: 'token', value: match }); lastIndex = index + match.length + 4; } parsed.push({ type: 'string', value: input.substring(lastIndex) }); console.log(parsed);

使用正则表达式:

 const convertToObjectArr = (str = '') => { const reg = /<%(.*?)%>/g; let arr = []; let index = 0, lastIndex = 0; while (match = reg.exec(str)) { index = match.index; if(index > lastIndex) { arr.push({ type: 'string', value: str.substring(lastIndex, index) }); } lastIndex = reg.lastIndex; arr.push({ type: 'token', value: str.substring(lastIndex-2, index+2) }); } if (lastIndex == 0) { arr.push({ type: 'string', value: str.substring(lastIndex) }); } else if (lastIndex < str.length) { arr.push({ type: 'token', value: str.substring(lastIndex) }); } return arr; } console.log( convertToObjectArr("Hello, I'm <%first%> <%last%>, and I <3 being a <%occupation%>. I am > blah") ); console.log( convertToObjectArr("Hello") ); console.log( convertToObjectArr("Hello, I'm <%first%>") );

这是我的方法。 如果您使用正则表达式,您可以简化很多(这基本上是正则表达式的确切用例)

 target = "Hello, I'm <%first%> <%last%>, and I <3 being a <%occupation%>. I am > blah" const split = (el) => { const parts = el.split('%>') return [{type: 'token', value: parts[0]}, {type: 'string', value: parts[1]}] } const parts = target.split('<%').map(el => el.indexOf('%>') === -1? {type: "string", value: el}: split(el) ).flat() console.log(parts)

您可以使用词法分析器来标记您的字符串。 我在这个例子中使用了moo

 const lexer = moo.compile({ token: {match: /<%.+?%>/, value: raw => raw.slice(2, -2)}, strlt: /.+?(?=<%)/, strrt: /(?<=%>).+/ }); lexer.reset("Hello, I'm <%first%> <%last%>, and I <3 being a <%occupation%>. I am > blah"); console.log( [...lexer].map(({ type, value }) => ({ type: (type === 'token'? type: 'string'), value })) );
 <script src="https://unpkg.com/moo@0.5.1/moo.js"></script>

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM