网页爬虫抓取百度图片(怎么老是静不下心来心来搞定一方面的技术,再学点其他的东西)

优采云 发布时间: 2022-03-31 00:26

  网页爬虫抓取百度图片(怎么老是静不下心来心来搞定一方面的技术,再学点其他的东西)

  我对xmfdsh真的很感兴趣,为什么不能静下心来搞定一个方面的技术,然后再学习其他的东西,一步一步来,好吧,我又要去学习网络爬虫了,这是一个简单的版本,参考网上很多资料,用C#写的,专门抓图,可以抓一些需要cookies的网站,所以功能还是挺全的,xmfdsh才研究了三天,所以有仍有很大的改进空间。我会慢慢改进的。我将在本文末尾附上整个项目。献给喜欢学习C#的朋友。让我慢慢说:

  #region 访问数据 + Request(int index)

///

/// 访问数据

///

private void Request(int index)

{

try

{

int depth;

string url = "";

//lock锁住Dictionary,因为Dictionary多线程会出错

lock (_locker)

{

//查看是否还存在未下载的链接

if (UnDownLoad.Count 0)

{

MemoryStream ms = new System.IO.MemoryStream(rs.Data, 0, read);

BinaryReader reader = new BinaryReader(ms);

byte[] buffer = new byte[32 * 1024];

while ((read = reader.Read(buffer, 0, buffer.Length)) > 0)

{

rs.memoryStream.Write(buffer, 0, read);

}

//递归 再次请求数据

var result = responseStream.BeginRead(rs.Data, 0, rs.BufferSize, new AsyncCallback(ReceivedData), rs);

return;

}

}

else

{

read = responseStream.EndRead(ar);

if (read > 0)

{

//创建内存流

MemoryStream ms = new MemoryStream(rs.Data, 0, read);

StreamReader reader = new StreamReader(ms, Encoding.GetEncoding("gb2312"));

string str = reader.ReadToEnd();

//添加到末尾

rs.Html.Append(str);

//递归 再次请求数据

var result = responseStream.BeginRead(rs.Data, 0, rs.BufferSize, new AsyncCallback(ReceivedData), rs);

return;

}

}

if (url.Contains(".jpg") || url.Contains(".png"))

{

//images = rs.Images;

SaveContents(rs.memoryStream.GetBuffer(), url);

}

else

{

html = rs.Html.ToString();

//保存

SaveContents(html, url);

//获取页面的链接

}

}

catch (Exception ex)

{

_reqsBusy[rs.Index] = false;

DispatchWork();

}

List links = GetLinks(html,url);

//得到过滤后的链接,并保存到未下载集合

AddUrls(links, depth + 1);

_reqsBusy[index] = false;

DispatchWork();

}

#endregion

  这就是数据的*敏*感*词*孩的图片),如果不是图片,我们认为是正常的html页面,然后阅读html代码,如果有链接http或 href,它将被添加到下载链接。当然,对于我们阅读的链接,我们已经限制了一些js或者一些css(不要阅读这样的东西)。

  private void SaveContents(byte[] images, string url)

{

if (images.Count() < 1024*30)

return;

if (url.Contains(".jpg"))

{

File.WriteAllBytes(@"d:\网络爬虫图片\" + _index++ + ".jpg", images);

Console.WriteLine("图片保存成功" + url);

}

else

{

File.WriteAllBytes(@"d:\网络爬虫图片\" + _index++ + ".png", images);

Console.WriteLine("图片保存成功" + url);

}

}

  #region 提取页面链接 + List GetLinks(string html)

///

/// 提取页面链接

///

///

///

private List GetLinks(string html,string url)

{

//匹配http链接

const string pattern2 = @"http://([\w-]+\.)+[\w-]+(/[\w- ./?%&=]*)?";

Regex r2 = new Regex(pattern2, RegexOptions.IgnoreCase);

//获得匹配结果

MatchCollection m2 = r2.Matches(html);

List links = new List();

for (int i = 0; i < m2.Count; i++)

{

//这个原因是w3school的网址,但里面的东西明显不是我们想要的

if (m2[i].ToString().Contains("www.w3.org"))

continue;

links.Add(m2[i].ToString());

}

//匹配href里面的链接,并加到主网址上(学网站的你懂的)

const string pattern = @"href=([""'])?(?[^'""]+)\1[^>]*";

Regex r = new Regex(pattern, RegexOptions.IgnoreCase);

//获得匹配结果

MatchCollection m = r.Matches(html);

// List links = new List();

for (int i = 0; i < m.Count; i++)

{

string href1 = m[i].ToString().Replace("href=", "");

href1 = href1.Replace("\"", "");

//找到符合的,添加到主网址(一开始输入的网址)里面去

string href = RootUrl + href1;

if (m[i].ToString().Contains("www.w3.org"))

continue;

links.Add(href);

}

return links;

}

#endregion

  提取页面链接的方法,当阅读发现这是html代码时,继续解释里面的代码,找到里面的url链接,这正是拥有网络爬虫功能的方法(不然会很无聊只提取这个页面),这里当然应该提取http链接,href中的字是因为。. . . (学网站就知道了,不好解释) 几乎所有的图片都放在里面,文章,所以上面有href之类的代码要处理。

  #region 添加url到 UnDownLoad 集合 + AddUrls(List urls, int depth)

///

/// 添加url到 UnDownLoad 集合

///

///

///

private void AddUrls(List urls, int depth)

{

lock (_locker)

{

if (depth >= MAXDEPTH)

{

//深度过大

return;

}

foreach (string url in urls)

{

string cleanUrl = url.Trim();

int end = cleanUrl.IndexOf(' ');

if (end > 0)

{

cleanUrl = cleanUrl.Substring(0, end);

}

if (UrlAvailable(cleanUrl))

{

UnDownLoad.Add(cleanUrl, depth);

}

}

}

}

#endregion

  #region 开始捕获 + DispatchWork()

///

/// 开始捕获

///

private void DispatchWork()

{

for (int i = 0; i < _reqCount; i++)

{

if (!_reqsBusy[i])

{

Request(i);

Thread.Sleep(1000);

}

}

}

#endregion

  此功能是为了使这些错误起作用。_reqCount 的值在开头设置。事实上,视觉上的理解就是你发布的 bug 的数量。在这个程序中,我默认放了20个,可以随时修改。对于一些需要cookies的网站,就是通过访问开头输入的URL,当然也可以使用HttpWebRequest辅助类,cookies = request.CookieContainer; //保存cookie,以后访问后续URL时添加就行 request.CookieContainer = cookies; //饼干尝试。对于 网站 只能通过应用 cookie 访问,不需要根网页,就像不需要百度图片的 URL,但如果访问里面的图片很突然,cookie会附上,所以这个问题也解决了。xmfdsh 发现这个程序中还有一些网站不能抓图。当捕捉到一定数量的照片时它会停止。具体原因不明,以后慢慢完善。

  附上源码:%E7%BD%91%E7%BB%9C%E7%88%AC%E8%99%AB.rar

0 个评论

要回复文章请先登录注册


官方客服QQ群

微信人工客服

QQ人工客服


线