【问题标题】:Get html forms and fields of string in Delphi在Delphi中获取html表单和字符串字段
【发布时间】:2015-11-13 12:37:53
【问题描述】:

我有一个系统,每 1 秒通过 GET 获取一个 html 来更新这个 html 中的系统数据可以有 1-20 个表单,需要获取所有表单并组装每个表单的查询字符串字段,我有一个函数这样做,问题是它比获取服务器html花费的时间更长,代码有什么问题?或者如何以不同的方式做到这一点?

procedure XThread.GetForms;
var
  sTemp, xResF : String;
  FormItem, v: Variant;
  Field: Variant;
  J, q, i, contCampos,
  tmForm : Integer;
  IDocForm : IHTMLDocument2;
begin
 IDocForm := CreateComObject(Class_HTMLDOcument) as IHTMLDocument2;
 v := VarArrayCreate([0, 0], VarVariant);
 v[0] := strFormMAT; //string html
 IDocForm.Write(PSafeArray(System.TVarData(v).VArray));
 IDocForm.Close;

 tmForm := (IDocForm.all.tags('FORM') as IHTMLElementCollection).Length;
 SetLength(matFormsArray, 0); //matFormsArray = Global Array of Array
 SetLength(matFormsArray, tmForm);
 for q := 0 to tmForm -1 do
   begin
    SetLength(matFormsArray[q], 2);

    FormItem := (IDocForm.all.tags('FORM') as IHTMLElementCollection).item(q, 0);
    xResF := '';
    sTemp := FormItem.Name;
    contCampos := FormItem.Length;
     for j := 0 to contCampos - 1 do
      begin
        Field := FormItem.Item(j);
        xResF := xResF + Field.Name + '=' + Field.Value;
        if j < FormItem.Length - 1 then
          xResF := xResF + '&';
      end;

      matFormsArray[q, 0] := sTemp;
      matFormsArray[q, 1] := xResF;
   end;
end;

strFormMAT =

<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
<html xmlns="http://www.w3.org/1999/xhtml">
<head>
<meta http-equiv="Content-Type" content="text/html; charset=utf-8" />
<title>Untitled Document</title>
</head>


<body>

 <form name="fprin" id="fprin">
   <input type="hidden" name="field11" value="value11"></input>
   <input type="hidden" name="field12" value="value12"></input>
   <input type="hidden" name="field13" value="value13"></input>
 </form>

 <table>
  <tr>
   <td>Title</td>
   <td>Title</td>
   <td>Title</td>
   <td>Title</td>
  </tr>

  <tr>
   <td>Value</td>
   <td>Value</td>
   <td>Value</td>
   <form name="xxx1" id="xxx1">
   <td>Value</td>
   <td>Value</td>
   <input type="hidden" name="field11" value="value11"></input>
   <input type="hidden" name="field12" value="value12"></input>
   <input type="hidden" name="field13" value="value13"></input>
   <input type="hidden" name="field14" value="value14"></input>
   </form>
  </tr>

  <tr>
   <td>Value</td>
   <td>Value</td>
   <td>Value</td>
   <form name="xxx2" id="xxx2">
   <td>Value</td>
   <td>Value</td>
   <input type="hidden" name="field21" value="value21"></input>
   <input type="hidden" name="field22" value="value22"></input>
   <input type="hidden" name="field23" value="value23"></input>
   <input type="hidden" name="field24" value="value24"></input>
   </form>
  </tr>

  <tr>
   <td>Value</td>
   <td>Value</td>
   <td>Value</td>
   <form name="xxx3" id="xxx3">
   <td>Value</td>
   <td>Value</td>
   <input type="hidden" name="field31" value="value31"></input>
   <input type="hidden" name="field32" value="value32"></input>
   <input type="hidden" name="field33" value="value33"></input>
   <input type="hidden" name="field34" value="value34"></input>
   </form>
  </tr>

  <tr>
   <td>Value</td>
   <td>Value</td>
   <td>Value</td>
   <form name="xxx4" id="xxx4">
   <td>Value</td>
   <td>Value</td>
   <input type="hidden" name="field41" value="value41"></input>
   <input type="hidden" name="field42" value="value42"></input>
   <input type="hidden" name="field43" value="value43"></input>
   <input type="hidden" name="field44" value="value44"></input>
   </form>
  </tr>

  <tr>
   <td>Value</td>
   <td>Value</td>
   <td>Value</td>
   <form name="xxx5" id="xxx5">
   <td>Value</td>
   <td>Value</td>
   <input type="hidden" name="field51" value="value51"></input>
   <input type="hidden" name="field52" value="value52"></input>
   <input type="hidden" name="field53" value="value53"></input>
   <input type="hidden" name="field54" value="value54"></input>
   </form>
  </tr>

  <tr>
   <td>Value</td>
   <td>Value</td>
   <td>Value</td>
   <form name="xxx6" id="xxx6">
   <td>Value</td>
   <td>Value</td>
   <input type="hidden" name="field61" value="value61"></input>
   <input type="hidden" name="field62" value="value62"></input>
   <input type="hidden" name="field63" value="value63"></input>
   <input type="hidden" name="field64" value="value64"></input>
   </form>
  </tr>


 </table>

</body>

</html>

我在线程中使用Synchronize(GetForms); 进行过程调用,但即使如此,也会崩溃且速度很慢。

我的问题是没有获取到html,它已经启动并运行,问题是提取html的形式,这个过程很慢

【问题讨论】:

  • 将您的解析器过程带到线程类之外。使其成为 tform 的本地过程,并使用方法“Synchronize”调用它。
  • 您正在使用基于 DOM 的解析器,它本身就很慢,因为它必须解析 HTML 并在内存中为每个 HTML 元素创建一个对象树。但更重要的是,您调用 IDocForm.all.tags('FORM') 的次数过多 - 一次是为了发现 &lt;form&gt; 元素的数量,然后在每次循环迭代时再次调用。不要那样做,这是浪费开销。调用一次并将生成的IHTMLElementCollection 保存到一个变量中,然后根据需要在该变量上调用item()
  • 在任何情况下,您都在寻找 HTML 中的特定内容,因此您应该考虑完全删除 DOM 解析器并使用简单的子字符串搜索+提取操作。那会快得多。或者至少切换到基于 SAX,或者更好的是基于 Reader 的 HTML 解析器,而不是基于 DOM 的解析器。
  • 可能是使用纯pascal HTML解析器。可悲的是我不知道任何免费的 - 只是这个付费的 - DIHtmlParser
  • 谢谢各位,我会寻找另一种使用html的方式,它确实是驱动最慢的应用程序,如果有人有任何提示,可以在各个地方使用,谢谢!

标签: html delphi dom ihtmldocument2


【解决方案1】:

您的问题并不完全清楚您要做什么,但看起来您应该研究一种与加载此自定义 HTML 代码的 HTMLDocument 不同的技术来完成这项工作。

如果需要使用由字段和值组成的查询字符串调用某个 URL,您应该查看 TIdHTTPany of the other components to perform a HTTP call directly(或 indirectly)。

【讨论】:

  • 你好,我的问题是没有获取到html,已经运行起来了,问题是提取html的形式,这个过程很慢。
  • 我添加了一个提取必要表单和字段的 html 代码模型
  • 我仍然完全不清楚你想用这个做什么。更不用说现在我认为您正在尝试提交表单似乎是错误的。
猜你喜欢
  • 2021-08-18
  • 1970-01-01
  • 1970-01-01
  • 2018-06-04
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2016-05-16
  • 2013-11-07
相关资源
最近更新 更多