Скачайте первые 1000 изображений из Google - программирование
Подтвердить что ты не робот

Скачайте первые 1000 изображений из Google

Я выполняю поиск изображений Google

http://www.google.com/search?hl=en&q=panda&bav=on.2,or.r_gc.r_pw.r_cp.r_qf.,cf.osb&biw=1287&bih=672&um=1&ie=UTF-8&tbm=isch&source=og&sa=N&tab=wi&ei=qW4FUJigJ4jWtAbToInABg

и результат - тысячи фотографий. Я ищу оболочку script, которая загрузит первые n изображения, например 1000 или 500.

Как я могу это сделать?

Я думаю, мне нужны некоторые расширенные регулярные выражения или что-то в этом роде. Я пытался много чего, но безрезультатно, может кто-нибудь мне помочь?

4b9b3361

Ответ 1

update 3: Я установил script для работы с phantomjs 2.x.

update 2: Я модифицировал script для использования phantomjs. Это сложнее установить, но, по крайней мере, это работает снова. http://sam.nipl.net/b/google-images http://sam.nipl.net/b/google-images.js

update 1: К сожалению, это больше не работает. Кажется, Javascript и другая магия теперь необходимы, чтобы найти, где находятся изображения. Вот версия script для поиска изображений yahoo: http://sam.nipl.net/code/nipl-tools/bin/yimg

оригинальный ответ: Я взломал что-то вместе для этого. Я обычно пишу меньшие инструменты и использую их вместе, но вы просили одну оболочку script, а не три десятка. Это намеренно плотный код.

http://sam.nipl.net/code/nipl-tools/bin/google-images

Кажется, что это очень хорошо. Пожалуйста, дайте мне знать, можете ли вы улучшить его или предложить какие-либо лучшие методы кодирования (учитывая, что это оболочка script).

#!/bin/bash
[ $# = 0 ] && { prog=`basename "$0"`;
echo >&2 "usage: $prog query count parallel safe opts timeout tries agent1 agent2
e.g. : $prog ostrich
       $prog nipl 100 20 on isz:l,itp:clipart 5 10"; exit 2; }
query=$1 count=${2:-20} parallel=${3:-10} safe=$4 opts=$5 timeout=${6:-10} tries=${7:-2}
agent1=${8:-Mozilla/5.0} agent2=${9:-Googlebot-Image/1.0}
query_esc=`perl -e 'use URI::Escape; print uri_escape($ARGV[0]);' "$query"`
dir=`echo "$query_esc" | sed 's/%20/-/g'`; mkdir "$dir" || exit 2; cd "$dir"
url="http://www.google.com/search?tbm=isch&safe=$safe&tbs=$opts&q=$query_esc" procs=0
echo >.URL "$url" ; for A; do echo >>.args "$A"; done
htmlsplit() { tr '\n\r \t' ' ' | sed 's/</\n</g; s/>/>\n/g; s/\n *\n/\n/g; s/^ *\n//; s/ $//;'; }
for start in `seq 0 20 $[$count-1]`; do
wget -U"$agent1" -T"$timeout" --tries="$tries" -O- "$url&start=$start" | htmlsplit
done | perl -ne 'use HTML::Entities; /^<a .*?href="(.*?)"/ and print decode_entities($1), "\n";' | grep '/imgres?' |
perl -ne 'use URI::Escape; ($img, $ref) = map { uri_unescape($_) } /imgurl=(.*?)&imgrefurl=(.*?)&/;
$ext = $img; for ($ext) { s,.*[/.],,; s/[^a-z0-9].*//i; $_ ||= "img"; }
$save = sprintf("%04d.$ext", ++$i); print join("\t", $save, $img, $ref), "\n";' |
tee -a .images.tsv |
while IFS=$'\t' read -r save img ref; do
wget -U"$agent2" -T"$timeout" --tries="$tries" --referer="$ref" -O "$save" "$img" || rm "$save" &
procs=$[$procs + 1]; [ $procs = $parallel ] && { wait; procs=0; }
done ; wait

Особенности:

  • менее 1500 байт
  • объясняет использование, если выполняется без аргументов
  • загружает полные изображения параллельно
  • вариант безопасного поиска
  • размер изображения, тип и т.д. opts string
  • параметры тайм-аута/повторов
  • олицетворяет googlebot для извлечения всех изображений
  • номера файлов изображений
  • сохраняет метаданные

Я выложу модульную версию некоторое время, чтобы показать, что ее можно сделать довольно хорошо с помощью набора сценариев оболочки и простых инструментов.

Ответ 2

Я не думаю, что вы можете выполнить всю задачу, используя только регулярные выражения. Есть 3 части этой проблемы -

1. Извлеките ссылки всех изображений ----- > Нельзя делать с помощью регулярных выражений. Для этого вам нужно использовать веб-язык. Google имеет API для этого программно. Ознакомьтесь с здесь и здесь.

2. Если вы на первом этапе выполнили какой-либо веб-язык, вы можете использовать следующее регулярное выражение, которое использует lookaheads для извлечения точного URL изображения

(?<=imgurl=).*?(?=&)

В приведенном выше выражении - Захватите все, начиная с imgurl=, и пока не встретите символ &. См. здесь для примера, где я взял URL-адрес первого изображения вашего результата поиска и извлек URL-адрес изображения.

Как я пришел к указанному выше регулярному выражению? Изучив ссылки изображений, найденных в поиске изображений.

3. Теперь у вас есть URL-адреса изображений, используйте веб-язык/инструмент для загрузки изображений.

Ответ 3

Вместо того, чтобы делать это в оболочке с регулярными выражениями, вам может быть проще, если вы используете что-то, что может фактически анализировать сам HTML, например PHP DOMDocument class.

Если вы застряли, используя только оболочку, и вам нужно очистить URL-адреса изображений, вам может быть совершенно не повезло. Регулярные выражения не подходят для разбора HTML, потому что HTML не является обычным языком. Но вы все равно сможете обойтись, если ваши исходные данные будут очень предсказуемыми. (Это не гарантирует, потому что Google регулярно обновляет свои продукты и услуги без предварительного уведомления.)

Тем не менее, в выводе URL-адреса, который вы указали в своем вопросе, каждый URL-адрес изображения, кажется, встроен в якорь, который ссылается на /imgres?…. Если мы сможем разобрать эти ссылки, мы можем собрать все, что нам нужно. В пределах этих ссылок URL-адреса изображений предшествуют &amp;imgurl=. Так что дайте очистить это.

#!/usr/local/bin/bash

# Possibly violate Google terms of service by lying about our user agent
agent="Mozilla/5.0 (X11; FreeBSD amd64; rv:12.0) Gecko/20100101 Firefox/12.0"

# Search URL
url="http://www.google.com/search?hl=en&q=panda&bav=on.2,or.r_gc.r_pw.r_cp.r_qf.,cf.osb&biw=1287&bih=672&um=1&ie=UTF-8&tbm=isch&source=og&sa=N&tab=wi&ei=qW4FUJigJ4jWtAbToInABg"

curl -A "$agent" -s -D- "$url" \
 | awk '{gsub(/<a href=/,"\n")} 1' \
 | awk '
   /imgres/ {
     sub(/" class=rg_l >.*/, "");       # clean things up
     split($0, fields, "\&amp;");       # gather the "GET" fields
     for (n=1; n<=length(fields); n++) {
       split(fields[n], a, "=");        # split name=value pair
       getvars[a[1]]=a[2];              # store in array
     }
     print getvars["imgurl"];           # print the result
   }
 '

Я использую две команды awk, потому что... ну, я ленив, и это был самый быстрый способ генерации строк, в которых я мог бы легко найти строку "imgres". Можно было потратить больше времени на эту очистку и сделать его более изящным, но закон уменьшения отдачи подсказывает, что это до тех пор, пока я пойду с этим.: -)

Этот script возвращает список URL-адресов, которые можно легко загрузить с помощью других инструментов оболочки. Например, если script называется getimages, то:

./getimages | xargs -n 1 wget

Обратите внимание, что Google, как представляется, передает мне только 83 результата (не 1000), когда я запускаю это с URL-адресом поиска, указанным в вашем вопросе. Возможно, это только первая страница, которую Google обычно передавал браузеру, прежде чем "расширить" страницу (используя JavaScript), когда я приблизился к дну. Правильный способ справиться с этим будет заключаться в использовании API поиска Google, в соответствии с ответом Павана и для оплаты данных Google, если вы делаете более 100 запросов в день.

Ответ 4

Сколько рабочей нагрузки? Почему бы не использовать Bulk Image Downloader? Он имеет 100 ограничений изображения.

И нужно кодирование для сайтов, имеющих просмотрщик изображений Java.

Ответ 5

Вместо того, чтобы пытаться проанализировать HTML (что очень сложно и может сломаться), рассмотрите API, выделенный @Paven в его ответе.

Кроме того, рассмотрите возможность использования инструмента, который уже пытается сделать что-то подобное. WGET (web-get) имеет функцию паука, подходящую для ссылок (в частности, для определенных типов файлов). См. Этот ответ на вопрос StackOverflow 'как использовать wget для загрузки всех изображений в одну папку.

Regex чудесно полезен, но я не думаю, что это в этом контексте - помните мантру Regex:

Некоторые люди, столкнувшись с проблемой, думают: "Я знаю, я буду использовать регулярные выражения". Теперь у них есть две проблемы.

- Джейми Завински

Ответ 6

с ответом Pavan Manjunath, если вы хотите высоту и ширину изображения

(?<=imgurl=)(?<imgurl>.*?)(?=&).*?(?<=h=)(?<height>.*?)(?=&).*?(?<=w=)(?<width>.*?)(?=&)

Вы получаете 3 группы регулярных выражений imgurl, высоту и ширину с информацией.

Ответ 7

Я нашел более простой способ сделать этот инструмент Я могу подтвердить, что он хорошо работает с этой записью. screenshot

Запросы функций разработчику:

  • Получить предварительный просмотр изображения (ов), чтобы убедиться в его правильности.
  • Разрешить ввод нескольких терминов последовательно (т.е. пакетная обработка).

Ответ 8

Python script: скачать изображения с полным разрешением из Google Image Search в настоящее время он загружает 100 изображений за запрос

from bs4 import BeautifulSoup
import requests
import re
import urllib2
import os
import cookielib
import json

def get_soup(url,header):
    return BeautifulSoup(urllib2.urlopen(urllib2.Request(url,headers=header)),"html.parser")


query = raw_input("query image")# you can change the query for the image  here
image_type="ActiOn"
query= query.split()
query='+'.join(query)
url="https://www.google.co.in/search?q="+query+"&source=lnms&tbm=isch"
print url
#add the directory for your image here
DIR="C:\\Users\\Rishabh\\Pictures\\"+query.split('+')[0]+"\\"
header={'User-Agent':"Mozilla/5.0 (Windows NT 6.1; WOW64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/43.0.2357.134 Safari/537.36"
}
soup = get_soup(url,header)


ActualImages=[]# contains the link for Large original images, type of  image
for a in soup.find_all("div",{"class":"rg_meta"}):
    link , Type =json.loads(a.text)["ou"]  ,json.loads(a.text)["ity"]
    ActualImages.append((link,Type))

print  "there are total" , len(ActualImages),"images"


###print images
for i , (img , Type) in enumerate( ActualImages):
    try:
        req = urllib2.Request(img, headers={'User-Agent' : header})
        raw_img = urllib2.urlopen(req).read()
        if not os.path.exists(DIR):
            os.mkdir(DIR)
        cntr = len([i for i in os.listdir(DIR) if image_type in i]) + 1
        print cntr
        if len(Type)==0:
            f = open(DIR + image_type + "_"+ str(cntr)+".jpg", 'wb')
        else :
            f = open(DIR + image_type + "_"+ str(cntr)+"."+Type, 'wb')


        f.write(raw_img)
        f.close()
    except Exception as e:
        print "could not load : "+img
        print e

Я отправляю свое решение здесь оригинальное решение, которое я опубликовал по следующему вопросу: fooobar.com/questions/38525/...

Ответ 9

есть другие библиотеки на github - это выглядит неплохо https://github.com/Achillefs/google-cse

g = GoogleCSE.image_search('Ian Kilminster')
img = g.fetch.results.first.link
file = img.split('/').last
File.open(file,'w') {|f| f.write(open(img).read)} 
`open -a Preview #{file}`