2016-07-26 2 views
0

Какой лучший способ для этого: у меня есть txt-файл, заполненный веб-адресами, я должен проверить все из них с помощью компонента idHTTP, только простая проверка из Интернета сервер, загрузка html и поиск соответствия, я хочу, чтобы он был быстрым, есть разные типы потоков, и я не уверен, что лучше всего использовать, TParallel for или Task threads или обычные темы? Я пробовал до TParallel for, и я застрял в AV, также я пробовал Task threads, но его не быстро, HTTP-запрос становится медленнее по времени, я также пробовал обычные потоки, и я не знал, как его использовать, потому что его сложно использовать ,
примечание: Пожалуйста, НЕ спускайте вниз, мне просто нужен совет от экспертов. СпасибоКакой лучший подход сделать http-запрос

+1

Что вы подразумеваете под «проверкой»? Вы имеете в виду загружать только заголовки? Проверьте, является ли он действительным URL-адресом или нет? Проверьте некоторые данные/содержимое, найденные на этом URL-адресе? Является ли ваш реальный вопрос, следует ли использовать «TParallel» или «TTask» для вашей цели? В любом случае, все эти вопросы - это широкие вопросы, которые привлекают упрямые ответы - оба из которых не одобряются здесь. что ты уже испробовал? Какие плюсы и минусы вы сами наблюдали между этими двумя возможными решениями? –

+0

@JerryDodge Загрузка html и поиск соответствия, добавление информации. – cyberdude

ответ

1

Первый совет: не используйте Indy. Использовать THTTPClient (единица System.Net.HttpClient) - родной для Delphi XE? +

Я все еще использую старые TThreads. Я мог бы сделать предложение только с TThread.

Workflow:

Основная нить - читать ваш TXT файл построчно. После того, как строка была прочитана, вы создаете NEW thread, который загружает информацию из WWW.

Пример применения:

unit ufmMain; 

interface 

uses 
    Winapi.Windows, Winapi.Messages, 
    System.SysUtils, System.Variants, 
    { TThread } 
    System.Classes, 
    Vcl.Graphics, Vcl.Controls, Vcl.Forms, Vcl.Dialogs, Vcl.StdCtrls; 

type 
    TForm1 = class(TForm) 
    Button1: TButton; 
    procedure Button1Click(Sender: TObject); 
    private 
    { Private declarations } 
    public 
    { Public declarations } 
    end; 

    TLoad = class(TThread) 
    protected 
    FURL, 
    FOutputFileName: String; 

    procedure Execute; override; 
    public 
    constructor Create(const AURL, AOutputFileName: String); overload; 
    end; 

    HTTP = class 
    public 
    class procedure Get(const AURL: String; out AOutputStream: TMemoryStream); 
    end; 

var 
    Form1: TForm1; 

implementation 

{$R *.dfm} 

uses 
    { THTTPClient } 
    System.Net.HttpClient; 

procedure TForm1.Button1Click(Sender: TObject); 
var 
    LLoad: TLoad; 
    LFile: TextFile; 
    LCycle: Integer; 
    LUrl: String; 
begin 
    LCycle := 0; 

    AssignFile(LFile, 'urls.txt'); 
    try 
    Reset(LFile); 

    while not Eof(LFile) do 
     begin 
     { Using for generate file name. All file names must be unique } 
     Inc(LCycle); 

     { Read next URL } 
     ReadLn(LFile, LUrl); 

     { Create new thread } 
     LLoad := TLoad.Create(LUrl, 'Output file No ' + LCycle.ToString + '.htm'); 
     LLoad.FreeOnTerminate := True; 
     LLoad.Start; 
     end; 
    finally 
    CloseFile(LFile); 
    end; 
end; 

{ TLoad } 

constructor TLoad.Create(const AURL, AOutputFileName: String); 
begin 
    inherited Create(True); 

    FURL := AURL; 
    FOutputFileName := AOutputFileName; 
end; 

procedure TLoad.Execute; 
var 
    LResponse: TMemoryStream; 
begin 
    inherited; 

    LResponse := TStringStream.Create; 
    try 
    HTTP.Get(FURL, LResponse); 

    { Save result to file } 
    LResponse.SaveToFile(GetCurrentDir + PathDelim + FOutputFileName); 
    finally 
    LResponse.Free; 
    end; 
end; 

{ HTTP } 

class procedure HTTP.Get(const AURL: String; out AOutputStream: TMemoryStream); 
var 
    LStream: TStream; 
    LHTTPClient: THTTPClient; 
begin 
    LHTTPClient := THTTPClient.Create; 
    try 
    LStream := LHTTPClient.Get(AURL).ContentStream; 

    AOutputStream.CopyFrom(LStream, LStream.Size); 
    finally 
    LHTTPClient.Free; 
    end; 
end; 

end. 

Почему я против Инди:

1) THTTPClient не требуется дополнительных DLL для работы с протоколом SSL

2) THTTPClient современный из Delphi X Е8

3) Мое субъективное мнение: THTTPClient работает намного плавно (с меньшим количеством проблем), а затем Indy library. Я использовал Indy последние 10 лет, но теперь весь мой поддерживаемый проект переместился в THTTPClient.

+0

Почему вы советуете использовать Indy? – mjn42

+0

@ mjn42 - Почему я против Инди: 1) THTTPClient не требуется дополнительных DLL для работы с протоколом SSL 2) THTTPClient современный из Delphi X Е8 3) Мое субъективное мнение: THTTPClient работает гораздо более плавно (с меньше проблем), а затем Indy library. Я использовал Indy последние 10 лет, но теперь весь мой поддерживаемый проект переместился в THTTPClient. – Zam

+0

смотрите здесь [http://stackoverflow.com/posts/comments/64687148?noredirect=1] – cyberdude

0

Вы можете использовать TTask и Indy (TIdHTTP). Пример:

function GetUrl(const aUrl: string): ITask; 
begin 
    Result := TTask.Run(
    procedure 
    var 
     FOutput: string; 
     FHTTP: TIdHTTP; 
    begin 
     FHTTP:=TIdHTTP.Create(nil); 
     try 
     try 
      FOutput:=FHTTP.Get(aUrl); 
     except 
      // handle errors 
     end; 
     finally 
     FHTTP.Free; 
     end; 

     TThread.Synchronize(nil, 
     procedure 
     begin 
      ProcessOutput(FOutput); // send your output/result to main thread 
     end); 
    end); 
end; 

procedure TForm1.Button1Click(Sender: TObject); 
var 
    i: Integer; 
    list: TStringList; 
begin 
    list:=TStringList.Create; 
    try 
    list.LoadFromFile('yourfile.txt'); 

    // get all your urls 
    // you should control how many threads run at the same time 
    for i := 0 to list.Count-1 do 
     GetUrl(list[i]); 
    finally 
    list.Free; 
    end; 
end; 
+0

Я полагаю, что использование ShowMessage (FOutput); 'не очень хорошая идея. – Zam

+0

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

+0

Я использовал этот метод раньше, но этот пост-ответ становится медленнее по времени, если вы используете несколько сообщений внутри цикла – cyberdude