V2EX = way to explore
V2EX 是一个关于分享和探索的地方
现在注册
已注册用户请  登录
xudd
V2EX  ›  程序员

新人第一次提问,有没有大神知道如何用 js 的解析文本形式的 html 文件啊?

  •  
  •   xudd · 2016-06-01 10:37:21 +08:00 · 3500 次点击
    这是一个创建于 3079 天前的主题,其中的信息可能已经有所发展或是发生改变。
    因为硬件条件限制,无法用 java 在后台解析获取的网页,也不能用 iframe 在页面嵌入 ajax 获取到的 html 文件,只能用 js 的正则表达式等去解析 html 文件。求大神指条明路,拜托拜托
    24 条回复    2016-06-02 11:53:54 +08:00
    will0404
        1
    will0404  
       2016-06-01 10:44:00 +08:00
    浏览器端不清楚 ,如果是 node 环境可以用 cheerio 这个库
    xudd
        2
    xudd  
    OP
       2016-06-01 10:45:42 +08:00
    @will0404 恩,能用 node 的确就简单了,可是我们的机顶盒浏览器只有 100M 内存。。。。
    zenxds
        3
    zenxds  
       2016-06-01 10:53:53 +08:00
    用 createFragment 不就可以了
    imn1
        4
    imn1  
       2016-06-01 11:00:56 +08:00
    导入到不可视元素就可以 DOM 了
    loading
        5
    loading  
       2016-06-01 11:04:35 +08:00 via Android
    没有用过 js 吗?
    如果是固定的 html ,用 jQuery 就能处理了。
    zhouyg
        6
    zhouyg  
       2016-06-01 12:17:41 +08:00
    可以用 jquery 中带的那个搜索器
    Arrowing
        7
    Arrowing  
       2016-06-01 12:23:57 +08:00
    jquery 就可以吧
    $('html')
    $('<html></html>') //文本内容
    xudd
        8
    xudd  
    OP
       2016-06-01 14:40:12 +08:00
    @zenxds 谢谢,我不是要获取创建元素,是要解析 html 文件中元素的内容,获取图片地址,标题和描述等
    xudd
        9
    xudd  
    OP
       2016-06-01 14:40:40 +08:00
    @imn1 类似于 iframe 吗?
    bigcoon
        10
    bigcoon  
       2016-06-01 14:41:19 +08:00
    正则
    xudd
        11
    xudd  
    OP
       2016-06-01 14:52:35 +08:00
    @zhouyg 搜索器是什么?
    xudd
        12
    xudd  
    OP
       2016-06-01 14:53:40 +08:00
    @bigcoon 现在就是用的正则,可是不知道为什么会卡死浏览器,我的代码是这样的
    function doAjaxCall(the_request){
    $.ajax({
    type:"get",
    url:the_request,
    dataType:"html",
    success:function(result){
    var ol = result+"";
    var regTitle = /shelf-title-table[^.]*(\s*)[^.]*(\n)*(\r)*(.*)[^.]*(\?)*?menu-container/gm;
    var mTitle,proName;
    var reg = /yt-shelf-grid-item[^.]*(\s*)[^.]*(\n)*(\r)*(.*)[^.]*(\?)*?yt-shelf-grid-item/gm;
    var m,i=0;
    $("#program").empty();
    while(i<7){
    mTitle = regTitle.exec(ol)
    //alert(regTitle.lastIndex)
    proName = mTitle[0].match(/branded-page-module-title-text(\s*?)(.*?)<\/span>/)[0].replace("branded-page-module-title-text\">","").replace("</span>","");
    var str = '<div class="nav"><ul><li><span>'+proName+'</span></li></ul></div>'+
    '<div class="zd_con" id="zdCon'+i+'"><ul id="programList'+i+'">';
    var j = 0;
    strVertArr[i] = new Array();
    reg.lastIndex = regTitle.lastIndex;
    while(j<5){
    m = reg.exec(ol);
    var imgSrcURL = m[0].match(/src=".*?"/)[0].replace("src=\"","").replace("\"","");
    var aHref = m[0].match(/href="\S*?"/)[0].replace("href=\"","http://www.youtube.com").replace("\"","");
    var name = '';//m[0].match(/yt-lockup-title[^.]*?(\s*?)(.*?)<\/h3>/)[0].match(/title="\S*?"/)[0].replace("title=\"","").replace("\"","");
    var description = '';//m[0].match(/<li>[^.]*(.*)(\s*)(.*)[^.]*<\/li>/)[0].replace("<li>","").replace("</li><li>","-").replace("</li>","");
    if(j<5){
    if(j==0)
    str += '<li><a id="a'+i+j+'" onkeydown="changeHome(event,\'\')" onfocus="return false;" ';
    else
    str += '<li><a id="a'+i+j+'" onkeydown="changeLoc(event,\'\')" onfocus="return false;" ';
    str += ' href="javascript:goToPlay(\'' + aHref + '\');" class="scale-item movies big-cover">';
    str += '<img class="big-img" src="'+imgSrcURL+'" />';
    str += '<span class="wz"><h3>'+name+'</h3><p>' + description +'</p></span></a></li>';
    }
    strVertArr[i][j] = new AdItem(name,imgSrcURL,aHref,description);
    j++;
    //ol.replace(m[0]+"","");
    }
    //alert(reg.lastIndex)
    str += '</ul></div>';
    strArray[i] = str;
    i++;
    $("#program").append(str);
    //ol.replace(mTitle[0]+"","");
    }
    $("#program").css("margin-bottom","20px");
    $(".body-right").css("margin-top","0px");
    }
    });
    }
    xudd
        13
    xudd  
    OP
       2016-06-01 14:54:32 +08:00
    @Arrowing 可以给个简单的例子吗?
    pimin
        15
    pimin  
       2016-06-01 15:08:40 +08:00
    楼主这个 js 是运行在盒子的浏览器,还是 web 端的浏览器啊?
    如果是运行在盒子,不如中间加一层代理,就是做 API 返回 JSON,这样处理就简单得多,更省资源.
    盒子性能优先,正则处理 HTML 开销并不比后台处理小.
    loginv2
        16
    loginv2  
       2016-06-01 15:14:03 +08:00
    @xudd 不清楚问题所在 但是可以肯定的是 把+=这种拼接字符串 改成数组 push 每一行内容 最后 join 起来 是一种优化 字符串拼的越多的时候 效果越明显
    hronro
        17
    hronro  
       2016-06-01 15:28:30 +08:00
    有个思路,就是把文本形式的 html ,直接插入到一个 display:none 的 div 中去,这样相当于可以通过浏览器原生的方法来解析 HTML ,而不用自己手动写 JS 来解析。当然实际性能如何,还需要具体测试
    Arrowing
        18
    Arrowing  
       2016-06-01 17:09:57 +08:00
    @xudd 正则性能一般写的性能都很差,好的正则和不好的正则差别十分大,一般不建议这样使用。
    例子(不能跨域):
    $.ajax({
    type:"get",
    url: 'https://cn.v2ex.com/t/282675',
    dataType:"html",
    success:function(result){

    var htmlNode = $(result);
    console.log(htmlNode);

    }});
    iyangyuan
        19
    iyangyuan  
       2016-06-01 17:44:57 +08:00
    innerHTML
    ChiChou
        21
    ChiChou  
       2016-06-01 18:11:45 +08:00   ❤️ 1
    楼主你给的代码看得太累了。既然你已经用了 jQuery ,也没有跨域的问题,那么用 jQuery 可以直接把返回的 HTML 构建出 DOM 树,包装成 jQuery 对象去访问里面的 dom 节点。然后用 css Query 去定位元素,并根据需要取 html() 或者 text() 就可以了。

    一个参考的例子:

    http://stackoverflow.com/questions/20007721/parsing-returned-html-from-jquery-ajax-request
    xudd
        22
    xudd  
    OP
       2016-06-01 20:22:00 +08:00
    非常感谢各位的耐心帮助,很多朋友都有提到 jquery ,但是我刚开始不太理解,看到 @ChiChou 给的链接才明白是怎么使用的,就是一句 ol = $(result).find(".item-section");就可以跟 iframe 一样使用 DOM 树上的内容了。再次感谢各位的帮助。
    loginv2
        23
    loginv2  
       2016-06-02 08:48:56 +08:00
    @ChiChou 其实知道,新版测过。但是一直在写兼容老版本的代码 (说起来都是泪
    ChiChou
        24
    ChiChou  
       2016-06-02 11:53:54 +08:00
    @loginv2 楼主说的地方是机顶盒,肯定是 webkit 之类的了
    关于   ·   帮助文档   ·   博客   ·   API   ·   FAQ   ·   实用小工具   ·   1063 人在线   最高记录 6679   ·     Select Language
    创意工作者们的社区
    World is powered by solitude
    VERSION: 3.9.8.5 · 25ms · UTC 19:45 · PVG 03:45 · LAX 11:45 · JFK 14:45
    Developed with CodeLauncher
    ♥ Do have faith in what you're doing.