问题描述
我正在处理播放歌曲标签的一小段代码,但是我遇到了问题.
I'm working on a little piece of code playing handling song tabs, but i'm stuck on a problem.
我需要解析每首歌的制表符行,并进行拆分,以便一方面获得和弦,另一方面获得 words .
I need to parse each song tab line and to split it to get chunks of chords on the one hand, and words in the other.
每个块都像:
$line_chunk = array(
0 => //part of line containing one or several chords
1 => //part of line containing words
);
他们应该保持分组"状态.我的意思是,仅当函数达到和弦与单词之间的极限"时,它才应该拆分.
They should stay "grouped". I mean by this that it should split only when the function reaches the "limit" between chords and words.
我想我应该使用 preg_split 来实现这一目标.我进行了一些测试,但是我只能按和弦进行分割,而不能按和弦"进行分组:
I guess I should use preg_split to achieve this. I made some tests, but I've been only able to split on chords, not "groups" of chords:
$line_chunks = preg_split('/(\[[^]]*\])/', $line, -1, PREG_SPLIT_DELIM_CAPTURE | PREG_SPLIT_NO_EMPTY);
这些示例向您展示了我想要得到的:
Those examples shows you what I would like to get :
在不包含和弦的行上:
$input = '{intro}';
$results = array(
array(
0 => null,
1 => '{intro}
)
);
在仅包含和弦的行上:
$input = '[C#] [Fm] [C#] [Fm] [C#] [Fm]';
$results = array(
array(
0 => '[C#] [Fm] [C#] [Fm] [C#] [Fm]',
1 => null
)
);
在同时包含这两者的行上:
on a line containing both :
$input = '[C#]I’m looking for [Fm]you [G#]';
$results = array(
array(
0 => '[C#]',
1 => 'I’m looking for'
),
array(
0 => '[Fm]',
1 => 'you '
),
array(
0 => '[G#]',
1 => null
),
);
关于如何执行此操作的任何想法?
Any ideas of how to do this ?
谢谢!
推荐答案
preg_split
并非可行之路.在大多数情况下,当您要完成复杂的拆分任务时,尝试匹配您感兴趣的内容比尝试使用不容易定义分隔符进行拆分要容易得多.
preg_split
isn't the way to go. Most of the time, when you have a complicated split task to achieve, it's more easy to try to match what you are interested by instead of trying to split with a not easy to define separator.
一种preg_match_all
方法:
$pattern = '~ \h*
(?| # open a "branch reset group"
( \[ [^]]+ ] (?: \h* \[ [^]]+ ] )*+ ) # one or more chords in capture group 1
\h*
( [^[\n]* (?<=\S) ) # eventual lyrics (group 2)
| # OR
() # no chords (group 1)
( [^[\n]* [^\s[] ) # lyrics (group 2)
) # close the "branch reset group"
~x';
if (preg_match_all($pattern, $input, $matches, PREG_SET_ORDER)) {
$result = array_map(function($i) { return [$i[1], $i[2]]; }, $matches);
print_r($result);
}
分支重置组为每个分支保留相同的组编号.
注意:随时添加:
if (empty($i[1])) $i[1] = null;
if (empty($i[2])) $i[2] = null;
如果要获取空项目而不是空项目,请在地图功能中
in the map function if you want to obtain null items instead of empty items.
注意2:如果逐行工作,则可以从图案中删除\n
.
Note2: if you work line by line, you can remove the \n
from the pattern.
这篇关于使用preg_split分割和弦和单词的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持!