拆分、匹配关键字

时间:2022-11-09 05:37:52
如何在一篇文章内拆分和匹配关键字?例如以下文章:

姐弟恋真的没好结果吗?我老公比我小五岁,我们刚结婚那会几乎天天吵,本来感情基础就没打好,结婚不久又有了孩子,孩子现在三岁了,在这三年里不知吵了多少会,可能现实生活就是这样的,两口子可能都吵过架,后来经过几次吵架,我也懂得了很多,两个人就的互相体谅,互相包容,忍让对方。我老公比较孩子气,动不动就发火,一点小事就生气,我们在一起这几年几乎没出去玩过,也没合过影,老公花钱也是没个计划,讲究名牌,吃也的要好的,不让买就生气要不不理你,自己老是有理的不行,我们收入一般,他的花销远远超出我们的收入,我是急在心里也不知怎么办,因为他不听你说,他还挺高傲自己认为别人都不如他,说我是傻逼,什么也不懂,真不知道你怎么长大的,就这样我也忍了,谁让我当初选的,还有为了孩子我可以忍,就是希望有一天他能发现自己也有错误,可是最近我发现我越忍让他越张狂,出去干活了,就的给你找点事干,说我出去挣钱养你们,你就不能闲着,好了你说干什么我干忍了,看见我没穿袜子说把我脚剁了,我也忍了,我不想和他吵没意思的,晚上回来饭做好了,吃了饭要吃烤红薯,我说给你弄去,需要买去,他说他姐夫说跑黑车,我说你也去吧,就这句话不爱听了,说我掉钱眼里了,就急了说我什么也不想,就会瞎BB,反正什么难听说什么,说我不干活,怎么不我不去挣钱,我说现在孩子小不能自理,我管好孩子就是我的任务,你应该出去挣钱,我说等子上学了我自然就挣去了,我说了他应该管,又不对,说凭什么我应该管你们呀,又急了就开始发疯了一直在说些他自己认为的事把我想想的特别坏,还的让你承认他说的对,我无语了不说了,让着他让他说,他又嫌你不说,我说你大人不计小人过我错了你就包容我一下吧别生气他说不行没完接着又是一顿数落,我现在都不知该如何是好,我忍让他那么多是让他从中得到点领悟,人无完人,把自己不对的也改改,发现点自己的缺点,但是没有反而更猖狂了,我又不是一个智慧的女人我现在该怎么办,希望大家帮帮忙,我很需要你们谢谢啦!



我想在用户发表该文章时,把文章的某些词语记录下来作为关键字以作他用。有没有什么算法/思路可以实现这个需求呢?还是只能人工阅读然后总结/抽出关键字?

16 个解决方案

#1


1.有关键词表(可以添加)
2.计算关键词频率

不要自己做分词,呵呵
编辑(这里指的人/职位)还是需要的

#2


1 系统关键字表, 会自动匹配替换关键字。
2 用户录入时指定关键字

#3


系统关键字表,指的是由我自己先录入好需要匹配的关键字,然后再到文章内匹配?

#4


引用 3 楼 natici 的回复:
系统关键字表,指的是由我自己先录入好需要匹配的关键字,然后再到文章内匹配?

是的。

#5


    可能我的需求描述的不够清晰吧。其实我就是想知道,是否有算法可以实现智能抓取文章中的词语作为关键字自动记录到数据库中去。然后再用这些关键字做其他用途。

#6


你的要求需要
1.分词系统
2.计算词频,选最多的N个

没那么只能的,至少目前是这样,放弃这个想法吧

#7


楼上是“没那么智能的”

#8


那看来只能是人工维护关键字表了。

#9


引用 5 楼 natici 的回复:
可能我的需求描述的不够清晰吧。其实我就是想知道,是否有算法可以实现智能抓取文章中的词语作为关键字自动记录到数据库中去。然后再用这些关键字做其他用途。

我理解你的意思是这样的:统计出文章中出现的字组合的频率,将频率高的作为关键字
这是可以做到的,只是 字组合 和 词语 并不是一回事

如果只是计算 字组合 还是很简单的,需要的话,等会给你代码

#10


唠叨说的也可行,至少可以简化一些步骤

不用分词,给出“字组合”频率,然后再人工挑选,适合手忙脚乱的时候不看文章,只选有词义的“字组合”

#11


引用 9 楼 xuzuning 的回复:
引用 5 楼 natici 的回复:可能我的需求描述的不够清晰吧。其实我就是想知道,是否有算法可以实现智能抓取文章中的词语作为关键字自动记录到数据库中去。然后再用这些关键字做其他用途。
我理解你的意思是这样的:统计出文章中出现的字组合的频率,将频率高的作为关键字
这是可以做到的,只是 字组合 和 词语 并不是一回事

如果只是计算 字组合 还是很简单的,需要的话,……


哦,字组合的话我也想看看是怎么实现的。那就麻烦老大给代码了。

#12


说明:
1、我使用的编码是 gbk 的,如果是 utf-8 的请自行删除有关编码的部分
2、处理用的文档时楼主贴出的示例文字
3、代码是现写的,有关算法问题请指正
iconv_set_encoding("internal_encoding", "utf-8");
iconv_set_encoding("output_encoding", "gbk");
ob_start("ob_iconv_handler"); 

$fn = '如何在一篇文章内拆分和匹配关键字_例文.txt';

$p = new T;
$ar = $p->parse($fn);
print_r($ar);
//print_r($p->dat);

class T {
  var $maxlen = 4;//最大组词长度
  var $dat = array();
  var $dict = array();
  function get($offs=0) {
    if($this->i + $offs >= $this->len || $offs >= $this->maxlen) return false;
    $ch = $this->doc[$this->i + $offs];
    if(in_array($ch, $this->dict)) return false;
    return $ch;
  }
  function parse($filename) {
    $this->dict = explode('|', iconv('gbk', 'utf-8', ',|。|;|:|“|”|?'));
    $s = file_get_contents($filename);
    $s = iconv('gbk', 'utf-8', $s);
    preg_match_all('/./u', $s, $r);
    $this->doc = $r[0];
    $this->i = 0;
    $this->len = count($this->doc);
    while($this->i < $this->len) {
      if(($ch = $this->get()) !== false) {
        if(! isset($this->dat[$ch]))
          $this->dat[$ch] = array('_v' => 0);
        else $this->dat[$ch]['_v']++;
        $this->next($this->dat[$ch], 1);
      }
      $this->i++;
    }
    $res = array();
    foreach($this->sortout($this->dat) as $r) {
      if(! isset($res[$r[0]])) $res[$r[0]] = 0;
      $res[$r[0]] += $r[1];
    }
    arsort($res);
    return $res;
  }
  function next(&$p, $offs) {
    if(($c = $this->get($offs)) === false) return;
    if(! isset($p[$c])) $p[$c] = array('_v' => 0);
    else $p[$c]['_v']++;
    $this->next($p[$c], $offs+1);
  }
  function sortout($dat, $word='', $num=0) {
    $res = array();
    foreach($dat as $key=>$item) {
      if($key != '_v' && $item['_v'] > 0) {
        if($num > 1) $res[] = array($word, $item['_v']+1); //只取两字及以上组合
        $res = array_merge($res, $this->sortout($item, $word.$key, $num+1));
      }
    }
    return $res;
  }
}


Array
(
    [什么] => 4
    [去挣] => 3
    [自己认] => 2
    [自己] => 2
    [出去挣] => 2
    [己认] => 2
    [怎么] => 2
    [应该] => 2
    [什么也] => 2
    [么也] => 2
    [出去] => 2
    [忍让] => 2
    [我说] => 2
    [我也忍] => 2
    [我也] => 2
    [我老公] => 2
    [我现] => 2
    [老公] => 2
    [也忍] => 2
    [了孩] => 2
    [就生] => 2
    [我老] => 2
)

#13


代码看得不太懂。我这边测试的结果是这样的:

Notice: iconv() [function.iconv]: Detected an incomplete multibyte character in input string in 1.php on line 212
Array ( [,我] => 11 [了,] => 6 [,说] => 4 [什么] => 4 [忍了] => 3 [去挣] => 3 [钱,] => 2 [己认] => 2 [钱,我] => 2 [怎么] => 2 [自己] => 2 [自己认] => 2 [么办] => 2 [挣钱] => 2 [挣钱,] => 2 [应该] => 2 [什么也] => 2 [说,] => 2 [去挣钱] => 2 [么也] => 2 [怎么办] => 2 [出去] => 2 [我现] => 2 [老公] => 2 [我说] => 2 [我也忍] => 2 [我老公] => 2 [我也] => 2 [,我说] => 2 [,就] => 2 [忍让] => 2 [我老] => 2 [也忍了] => 2 [也忍] => 2 [就生] => 2 [了孩] => 2 [出去挣] => 2 )


其中212行:
$this->dict = explode('|', iconv('gbk', 'utf-8', ',|。|;|:|“|”|?'));


能否大概描述下每个方法的用途?

#14


先把它拆分成词语,找出名词
根据词语出现的频率 设置系统关键字进行匹配
但是感觉设制关键字那规模得多庞大啊

#15


哦,我明白这个类的思路了,这种字频度的组合跟我的需求还是有点出入。
无论如何,还是要谢谢老大的付出!感谢各位的回复!

#16


该回复于2012-12-20 09:17:02被管理员删除

#1


1.有关键词表(可以添加)
2.计算关键词频率

不要自己做分词,呵呵
编辑(这里指的人/职位)还是需要的

#2


1 系统关键字表, 会自动匹配替换关键字。
2 用户录入时指定关键字

#3


系统关键字表,指的是由我自己先录入好需要匹配的关键字,然后再到文章内匹配?

#4


引用 3 楼 natici 的回复:
系统关键字表,指的是由我自己先录入好需要匹配的关键字,然后再到文章内匹配?

是的。

#5


    可能我的需求描述的不够清晰吧。其实我就是想知道,是否有算法可以实现智能抓取文章中的词语作为关键字自动记录到数据库中去。然后再用这些关键字做其他用途。

#6


你的要求需要
1.分词系统
2.计算词频,选最多的N个

没那么只能的,至少目前是这样,放弃这个想法吧

#7


楼上是“没那么智能的”

#8


那看来只能是人工维护关键字表了。

#9


引用 5 楼 natici 的回复:
可能我的需求描述的不够清晰吧。其实我就是想知道,是否有算法可以实现智能抓取文章中的词语作为关键字自动记录到数据库中去。然后再用这些关键字做其他用途。

我理解你的意思是这样的:统计出文章中出现的字组合的频率,将频率高的作为关键字
这是可以做到的,只是 字组合 和 词语 并不是一回事

如果只是计算 字组合 还是很简单的,需要的话,等会给你代码

#10


唠叨说的也可行,至少可以简化一些步骤

不用分词,给出“字组合”频率,然后再人工挑选,适合手忙脚乱的时候不看文章,只选有词义的“字组合”

#11


引用 9 楼 xuzuning 的回复:
引用 5 楼 natici 的回复:可能我的需求描述的不够清晰吧。其实我就是想知道,是否有算法可以实现智能抓取文章中的词语作为关键字自动记录到数据库中去。然后再用这些关键字做其他用途。
我理解你的意思是这样的:统计出文章中出现的字组合的频率,将频率高的作为关键字
这是可以做到的,只是 字组合 和 词语 并不是一回事

如果只是计算 字组合 还是很简单的,需要的话,……


哦,字组合的话我也想看看是怎么实现的。那就麻烦老大给代码了。

#12


说明:
1、我使用的编码是 gbk 的,如果是 utf-8 的请自行删除有关编码的部分
2、处理用的文档时楼主贴出的示例文字
3、代码是现写的,有关算法问题请指正
iconv_set_encoding("internal_encoding", "utf-8");
iconv_set_encoding("output_encoding", "gbk");
ob_start("ob_iconv_handler"); 

$fn = '如何在一篇文章内拆分和匹配关键字_例文.txt';

$p = new T;
$ar = $p->parse($fn);
print_r($ar);
//print_r($p->dat);

class T {
  var $maxlen = 4;//最大组词长度
  var $dat = array();
  var $dict = array();
  function get($offs=0) {
    if($this->i + $offs >= $this->len || $offs >= $this->maxlen) return false;
    $ch = $this->doc[$this->i + $offs];
    if(in_array($ch, $this->dict)) return false;
    return $ch;
  }
  function parse($filename) {
    $this->dict = explode('|', iconv('gbk', 'utf-8', ',|。|;|:|“|”|?'));
    $s = file_get_contents($filename);
    $s = iconv('gbk', 'utf-8', $s);
    preg_match_all('/./u', $s, $r);
    $this->doc = $r[0];
    $this->i = 0;
    $this->len = count($this->doc);
    while($this->i < $this->len) {
      if(($ch = $this->get()) !== false) {
        if(! isset($this->dat[$ch]))
          $this->dat[$ch] = array('_v' => 0);
        else $this->dat[$ch]['_v']++;
        $this->next($this->dat[$ch], 1);
      }
      $this->i++;
    }
    $res = array();
    foreach($this->sortout($this->dat) as $r) {
      if(! isset($res[$r[0]])) $res[$r[0]] = 0;
      $res[$r[0]] += $r[1];
    }
    arsort($res);
    return $res;
  }
  function next(&$p, $offs) {
    if(($c = $this->get($offs)) === false) return;
    if(! isset($p[$c])) $p[$c] = array('_v' => 0);
    else $p[$c]['_v']++;
    $this->next($p[$c], $offs+1);
  }
  function sortout($dat, $word='', $num=0) {
    $res = array();
    foreach($dat as $key=>$item) {
      if($key != '_v' && $item['_v'] > 0) {
        if($num > 1) $res[] = array($word, $item['_v']+1); //只取两字及以上组合
        $res = array_merge($res, $this->sortout($item, $word.$key, $num+1));
      }
    }
    return $res;
  }
}


Array
(
    [什么] => 4
    [去挣] => 3
    [自己认] => 2
    [自己] => 2
    [出去挣] => 2
    [己认] => 2
    [怎么] => 2
    [应该] => 2
    [什么也] => 2
    [么也] => 2
    [出去] => 2
    [忍让] => 2
    [我说] => 2
    [我也忍] => 2
    [我也] => 2
    [我老公] => 2
    [我现] => 2
    [老公] => 2
    [也忍] => 2
    [了孩] => 2
    [就生] => 2
    [我老] => 2
)

#13


代码看得不太懂。我这边测试的结果是这样的:

Notice: iconv() [function.iconv]: Detected an incomplete multibyte character in input string in 1.php on line 212
Array ( [,我] => 11 [了,] => 6 [,说] => 4 [什么] => 4 [忍了] => 3 [去挣] => 3 [钱,] => 2 [己认] => 2 [钱,我] => 2 [怎么] => 2 [自己] => 2 [自己认] => 2 [么办] => 2 [挣钱] => 2 [挣钱,] => 2 [应该] => 2 [什么也] => 2 [说,] => 2 [去挣钱] => 2 [么也] => 2 [怎么办] => 2 [出去] => 2 [我现] => 2 [老公] => 2 [我说] => 2 [我也忍] => 2 [我老公] => 2 [我也] => 2 [,我说] => 2 [,就] => 2 [忍让] => 2 [我老] => 2 [也忍了] => 2 [也忍] => 2 [就生] => 2 [了孩] => 2 [出去挣] => 2 )


其中212行:
$this->dict = explode('|', iconv('gbk', 'utf-8', ',|。|;|:|“|”|?'));


能否大概描述下每个方法的用途?

#14


先把它拆分成词语,找出名词
根据词语出现的频率 设置系统关键字进行匹配
但是感觉设制关键字那规模得多庞大啊

#15


哦,我明白这个类的思路了,这种字频度的组合跟我的需求还是有点出入。
无论如何,还是要谢谢老大的付出!感谢各位的回复!

#16


该回复于2012-12-20 09:17:02被管理员删除