(отказ от ответственности: я сам не пробовал, так что принимайте это просто как пищу для экспериментов. 4 грамма в основном берутся из голубого неба, просто из моего опыта, что 3 грамма не будут работать слишком хорошо ; 5 граммов и более могут работать лучше, даже если вам придется иметь дело с довольно большим столом). Это также упрощенно в том смысле, что в нем не учитывается окончание строки - если это работает для вас иначе, вам, вероятно, придется подумать об исправлении окончаний.
Этот алгоритм будет работать в предсказуемое время, пропорциональное длине строки, которую вы пытаетесь разделить.
Итак, сначала: возьмите много читабельных текстов. для каждого текста, предполагая, что он находится в одной строке str , запустите следующий алгоритм (псевдокод-нотация, предполагается, что [] является индексацией, подобной хеш-таблице, и что несуществующие индексы возвращают '0' ):
for(i=0;i<length(s)-5;i++) {
// take 4-character substring starting at position i
subs2 = substring(str, i, 4);
if(has_space(subs2)) {
subs = substring(str, i, 5);
delete_space(subs);
yes_space[subs][position(space, subs2)]++;
} else {
subs = subs2;
no_space[subs]++;
}
}
Это создаст вам таблицы, которые помогут решить, нужно ли в данном 4-грамме вставлять пробел или нет.
Затем возьмите вашу строку для разделения, я обозначу ее как xstr и сделайте:
for(i=0;i<length(xstr)-5;i++) {
subs = substring(xstr, i, 4);
for(j=0;j<4;j++) {
do_insert_space_here[i+j] -= no_space[subs];
}
for(j=0;j<4;j++) {
do_insert_space_here[i+j] += yes_space[subs][j];
}
}
Затем вы можете пройтись по массиву " do_insert_space_here []" - если элемент в данной позиции больше 0, то вы должны вставить пробел в этой позиции в исходной строке. Если оно меньше нуля, то не стоит.
Пожалуйста, напишите здесь, если вы пытаетесь (или что-то в этом роде), и это работает (или не работает) для вас: -)