如何处理 Web 浏览器控件的线程

发布于 2024-10-01 00:56:35 字数 931 浏览 1 评论 0原文

我正在使用 BrowserControl 导航到网站上的网页范围,然后解析 html 并提取有关书籍等的信息...我遇到了(我认为)与线程相关的问题...

我有类似的问题。

// MAIN LOOP
for (int i = 0; i < NumberOfPages; i++)
 {
  WebBrowser.Navigate("http://AWebSite/" + NumberOfPages.ToString());
 }

// HANDLE ON_LOADED EVENT
 void WebBrowser_LoadCompleted(object sender, NavigationEventArgs e)
    {
   // Retrieve HTMLDocument, Parse it etc
    }

现在,由于控件导航到页面后需要几秒钟的时间才能触发事件,因此我有以下两个选项之一:

选项1 在我的主循环中等待几秒钟,如下所示:

for (int i = 0; i < NumberOfPages; i++)
{
  WebBrowser.Navigate("http://www.mysite.com"); 

// wait for 5 seconds
DateTime wait = new DateTime();
while (new DateTime().Ticks < wait.Ticks + 5000)  
    {
     // not sure if I need do events here         
    }
}

OPTION2 另一个想法是将全局变量作为(布尔)标志,向事件处理程序指示页面仍在下载(该标志在主外观中设置为忙,然后重置,然后在处理返回的 html 后重置)。

我感觉这两种方法都很笨拙,而且确实有更好的方法是以某种方式处理这两件事(在不同的线程上运行?)

I am using BrowserControl to navigate to range of web pages on a site and then parse the html and extract information about books etc… I am having problems related (I think) to threading…

I have something like this.

// MAIN LOOP
for (int i = 0; i < NumberOfPages; i++)
 {
  WebBrowser.Navigate("http://AWebSite/" + NumberOfPages.ToString());
 }

// HANDLE ON_LOADED EVENT
 void WebBrowser_LoadCompleted(object sender, NavigationEventArgs e)
    {
   // Retrieve HTMLDocument, Parse it etc
    }

Now since it takes a few seconds for the event to fire after the control navigates to a page, I have one of two options:

OPTION1
Wait a few seconds in my main loop, like this:

for (int i = 0; i < NumberOfPages; i++)
{
  WebBrowser.Navigate("http://www.mysite.com"); 

// wait for 5 seconds
DateTime wait = new DateTime();
while (new DateTime().Ticks < wait.Ticks + 5000)  
    {
     // not sure if I need do events here         
    }
}

OPTION2
Another idea is to a Global Variable as a (Boolean) Flag to indicate to the event handler that the page is still downloading (the flag is set to busy in the main look and then reset and then reset after after handling the html returned).

I have a feeling both of these approaches are clumsy and really that there is a better way is to somehow handle these two things (running on different threads?)

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(2

逆夏时光 2024-10-08 00:56:35

是的,延迟是很笨拙的——可能需要比这更长的时间或其他什么。

您需要 WebBrowser 控件吗?看起来你正在做一些批处理。如果是这样,System.Net.WebClient 可能适合您。它具有阻塞和异步方法 - .DownloadData 和 .DoanloadDataAsync。

如果您需要的话,我可能可以挖掘一些代码,但是快速搜索会显示一些示例。

Yeah, a delay is clumsy - it may take longer than that or whatever.

Do you need the WebBrowser control? It looks like you're doing some batch processing. If that's so, the System.Net.WebClient may work for you. It has blocking and asynchronous methods - .DownloadData and .DoanloadDataAsync.

I can probably dig up some code if you need it, but a quick search shows some examples out there.

朱染 2024-10-08 00:56:35

您可以通过误用迭代器来做到这一点,正如我此处所述。

例如:

interface IAction { void Execute(Action callback); }

public static void ExecAction(IEnumerator<IAction> enumerator) {
    if (enumerator.MoveNext())
        enumerator.Current.Execute(() => ExecAction(enumerator));
}

class WaitForLoad : IAction {
    void IAction.Execute(Action callback) {
       //Handle the LoadCompleted event and call callback
    }
}

IEnumerator<IAction> YourMethod() { 
    ...
    for (int i = 0; i < NumberOfPages; i++) {
        WebBrowser.Navigate("http://AWebSite/" + NumberOfPages.ToString());
        yield return new WaitForLoad();
    }
    ...
}

您可以通过使用 WaitForLoad 检查是否已加载正确的页面来使此过程变得更加复杂。

You can do this by misuing iterators, as I described here.

For example:

interface IAction { void Execute(Action callback); }

public static void ExecAction(IEnumerator<IAction> enumerator) {
    if (enumerator.MoveNext())
        enumerator.Current.Execute(() => ExecAction(enumerator));
}

class WaitForLoad : IAction {
    void IAction.Execute(Action callback) {
       //Handle the LoadCompleted event and call callback
    }
}

IEnumerator<IAction> YourMethod() { 
    ...
    for (int i = 0; i < NumberOfPages; i++) {
        WebBrowser.Navigate("http://AWebSite/" + NumberOfPages.ToString());
        yield return new WaitForLoad();
    }
    ...
}

You can make this more sophisticated by having WaitForLoad check that the correct page has loaded.

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文