https://github.com/HIT-SCIR/ltp/wiki/%E5%BC%80%E5%A7%8B%E4%BD%BF%E7%94%A8ltp
下面给出一个demo
package model.ner;
import model.bean.LtpRes;
import org.json.JSONException;
import org.json.JSONObject;
import util.IOUtil;
import java.io.BufferedReader;
import java.io.IOException;
import java.io.InputStreamReader;
import java.io.PrintWriter;
import java.net.URL;
import java.net.URLConnection;
import java.util.ArrayList;
import java.util.List;
import java.util.regex.Matcher;
import java.util.regex.Pattern;
/**
* Created by Macan on 2017/10/13.
*
* 在服务端搭建LTP service 服务,使用HTTP 请求进行NER标注, HTTP请求为POST请求
* 请求参数:
* s 输入字符串,在xml选项x为n的时候,代表输入句子;为y时代表输入xml
x 用以指明是否使用xml
c 用以指明输入编码方式
t 用以指明分析目标,t可以为分词(ws),词性标注(pos),命名实体识别(ner),依存句法分析(dp),语义角色标注(srl)或者全部任务(all)
*/
public class LtpServer {
/**
* 服务地址
*/
private final static String baseURL = "http://118.118.118.113:12345/ltp";
/**
* NLP task parameters 设置请求中的t参数
*/
private final static String defaultParameters = "t=ner&x=n";
/**
* 发送POST 请求到服务器中请求NER service
* @param url
* @param param
* @return
*/
public static String sendPost(String url, String param) {
boolean isBug = false;
PrintWriter out = null;
BufferedReader in = null;
URLConnection conn = null;
String result = "";
try {
URL realUrl = new URL(url);
// 打开和URL之间的连接
conn = realUrl.openConnection();
// 设置通用的请求属性
conn.setRequestProperty("accept", "*/*");
conn.setRequestProperty("connection", "Keep-Alive");
conn.setRequestProperty("user-agent",
"Mozilla/4.0 (compatible; MSIE 6.0; Windows NT 5.1;SV1)");
// 发送POST请求必须设置如下两行
conn.setDoOutput(true);
conn.setDoInput(true);
// 获取URLConnection对象对应的输出流
out = new PrintWriter(conn.getOutputStream());
// 发送请求参数
out.print(param);
// flush输出流的缓冲
out.flush();
// 定义BufferedReader输入流来读取URL的响应
in = new BufferedReader(
new InputStreamReader(conn.getInputStream()));
String line;
while ((line = in.readLine()) != null) {
result += line;
}
} catch (IOException e) {
System.out.println("发送 POST 请求出现异常!"+ e.getLocalizedMessage());
e.printStackTrace();
isBug = true;
System.out.println(param);
}
//使用finally块来关闭输出流、输入流
finally{
try{
if(out!=null){
out.close();
}
if(in!=null){
in.close();
}
}
catch(IOException ex){
ex.printStackTrace();
}
}
if (isBug){
return null;
}
return result;
}
/**
* 使用LTP 进行解析一句话,进行NER Task
* @param sentence 需要解析的句子
* 句子长度应该小于1024个字,256个词
* @return
*/
public static List parser(String sentence){
//设置请求参数
// String parameter = "s=" + sentence + "&" + defaultParameters;
return parser(sentence, defaultParameters);
}
/**
* 解析成List 格式数据
* @param sentence
* @param parameters
* @return
*/
public static List parser(String sentence, String parameters) {
sentence = sentence.replaceAll("[ ]+", " ");
if (sentence.equals("")) {
return null;
}
String strResult = "";
//如果需要处理的句子长度超过了1024个字符,进行切分处理,避免抛出异常,时间上的消耗
if (sentence.length() > 600){
for (String tmp : IOUtil.splitWithReg(sentence, "。|!|?|;|;|,|,")) {
String s = "s=" + tmp + "&" + parameters;
String rst = sendPost(baseURL, s);
//如果还是句子过长,继续更细粒度的切分
if (rst == null){
return null;
}
strResult += rst;
}
}else {
String p = "s=" + sentence + "&" + parameters;
//请求处理任务
strResult = sendPost(baseURL, p);
}
Pattern pattern = Pattern.compile("(?=\\{)(.+?)(?<=})");
if (strResult == null){
//处理句子过长问题,切分句子成两个较小的子句
for (String tmp : IOUtil.splitWithReg(sentence, "。|!|?|;|;|,|,")) {
String s = "s=" + tmp + "&" + parameters;
String rst = sendPost(baseURL, s);
//如果还是句子过长,继续更细粒度的切分
if (rst == null){
return null;
}
strResult += rst;
}
}
// 可能是網絡請求失敗
if (strResult == null) {
return null;
}
List result = new ArrayList<>();
//将xml结果转化为json
Matcher matcher = pattern.matcher(strResult);
while (matcher.find()) {
JSONObject object = null;
try {
object = new JSONObject(matcher.group());
}catch (JSONException e){
e.printStackTrace();
System.out.println(matcher.group());
}
result.add(new LtpRes(object.getString("cont"),
object.getInt("id"),
object.getString("ne"),
object.getString("pos")));
}
return result;
}
/**
* print
* @param data
*/
public static void show(List data) {
for (LtpRes ltpRes : data) {
System.out.println(ltpRes.getTerm() + "\t" +
ltpRes.getId() + "\t" +
ltpRes.getNer() + "\t" +
ltpRes.getPos() + "\t");
}
}
public static void main(String[] args) {
String data = "然后…… 献给天眼的诗 静旅游 天眼 我们静成没长嘴的稻草人 睡你怀里,体验 静,旅游 (一) “中国天眼”,什么都逃不脱 你的法眼,但你能 看穿善变的女人和多情的男人吗? 不管、不想、不看、不听、也不问 静成没长嘴的稻草人 睡你怀里,体验,探索 揭穿,天神合一的奥秘 (二) 五公里以外的手机,静默在 黑匣子里会不会心慌,会不会 想念,安静在帐篷里的我 反正,离开后,我总是左手拉着右手 伸进口袋里摸 你的影子 (三) 摸黑爬八百级木塑台阶,只为 看一眼你的夜色朦胧 细细弯弯的月里盛的光太浅,黑暗 念着咒语把恐惧变成手电筒 瞭望秒杀天际的虚幻 你和我一前一后,寻 那个叫天眼的那口锅,翻炒 昨日的温柔 溢出豆蔻年华的香 (四) 第一次住帐篷,身边有男人 保护 第二次住帐篷,身边有男人 守护 生长二十年的光阴,压碎 男人的脸,重叠 六年前,父亲摘下了最爱的那朵花 脸色苍白,头发也苍白 帐外上百人与虫叫蛙鸣合奏 交响曲,一浪高过一浪 我在海中安静划船,独享 远离尘嚣的畅快,直到 摇不动桨 天眼的秘密 田花 是谁静立群山之巅 却在谷底闭关,修炼 用天之眼 偷窥未知世界的喜悦 破译天神合一的秘密 赞赏苍穹臂弯的浩淼 是谁拉紧了馈源线 在几百米的高空架起馈源塔 正是这六名壮汉的坚守 才让生命之门打开 从此,平塘的白天黑夜不会孤单 因为全宇宙都在这,聚焦 世界的眼上帝的眼,再大 都比不上500米口径的那口“锅” 炒出一支天外的秘密之歌 光怪陆离,流光溢彩 与天地合拍 与梦想舞蹈 (作者来自花溪区新闻信息中心,系花溪区作协会员)";// String data = "";
String data2 = "我爱北京天安门,我爱北京。我爱旅游。";
String data3 = "记者 施昱凌 周滔 黄浩 不带手机等任何电子设备,体验两天“静旅游”。11月4日下午,经过两个小时的车程,参加此次网络媒体网络名人感知“中国天眼”FAST静旅游体验式集中采访活动的百余名大咖顺利抵达目的地。 从此刻开始,百余网媒网络名人将在静默区进行体验,集体下线20余个小时!他们将在这里回归大自然,用眼拍照,用心思考,用笔写作…… 此时无声胜有声! 真的好想你 亲爱的手机 5日早上,参加此次网络媒体网络名人感知“中国天眼”FAST静旅游体验式集中采访活动的百余名大咖回到现实中。 在享受了一段时间的静默时光之后,网媒网络名人纷纷拿回了自己的手机。 然后…… 献给天眼的诗 静旅游 天眼 我们静成没长嘴的稻草人 睡你怀里,体验 静,旅游 (一) “中国天眼”,什么都逃不脱 你的法眼,但你能 看穿善变的女人和多情的男人吗? 不管、不想、不看、不听、也不问 静成没长嘴的稻草人 睡你怀里,体验,探索 揭穿,天神合一的奥秘 (二) 五公里以外的手机,静默在 黑匣子里会不会心慌,会不会 想念,安静在帐篷里的我 反正,离开后,我总是左手拉着右手 伸进口袋里摸 你的影子 (三) 摸黑爬八百级木塑台阶,只为 看一眼你的夜色朦胧 细细弯弯的月里盛的光太浅,黑暗 念着咒语把恐惧变成手电筒 瞭望秒杀天际的虚幻 你和我一前一后,寻 那个叫天眼的那口锅,翻炒 昨日的温柔 溢出豆蔻年华的香 (四) 第一次住帐篷,身边有男人 保护 第二次住帐篷,身边有男人 守护 生长二十年的光阴,压碎 男人的脸,重叠 六年前,父亲摘下了最爱的那朵花 脸色苍白,头发也苍白 帐外上百人与虫叫蛙鸣合奏 交响曲,一浪高过一浪 我在海中安静划船,独享 远离尘嚣的畅快,直到 摇不动桨 天眼的秘密 田花 是谁静立群山之巅 却在谷底闭关,修炼 用天之眼 偷窥未知世界的喜悦 破译天神合一的秘密 赞赏苍穹臂弯的浩淼 是谁拉紧了馈源线 在几百米的高空架起馈源塔 正是这六名壮汉的坚守 才让生命之门打开 从此,平塘的白天黑夜不会孤单 因为全宇宙都在这,聚焦 世界的眼上帝的眼,再大 都比不上500米口径的那口“锅” 炒出一支天外的秘密之歌 光怪陆离,流光溢彩 与天地合拍 与梦想舞蹈 (作者来自花溪区新闻信息中心,系花溪区作协会员)";
List res = LtpServer.parser(data3);
System.out.println(data.length());
System.out.println(data.toCharArray().length);
LtpServer.show(res);
}
}
其中用到的数据结构LtpRes :
package model.bean;
import java.io.Serializable;
/**
* Created by Macan on 2017/10/13.
* LTP NER后返回的序列
*/
public class LtpRes implements Serializable {
private String term;
private int id;
private String ner;
private String pos;
public LtpRes() {
}
public LtpRes(String term, int id, String ner, String pos) {
this.term = term;
this.id = id;
this.ner = ner;
this.pos = pos;
}
@Override
public String toString() {
return "{" +
"term='" + term +
", id:" + id +
", ner:'" + ner +
", pos:'" + pos +
'}';
}
public String getTerm() {
return term;
}
public void setTerm(String term) {
this.term = term;
}
public int getId() {
return id;
}
public void setId(int id) {
this.id = id;
}
public String getNer() {
return ner;
}
public void setNer(String ner) {
this.ner = ner;
}
public String getPos() {
return pos;
}
public void setPos(String pos) {
this.pos = pos;
}
}