Cout исправляет ошибку в программе на C ++, но почему? - PullRequest
2 голосов
/ 22 октября 2010

Я написал простую программу для получения цен на акции от финансов Yahoo. Цикл, который считывает данные, усекался рано (и заканчивался тем, где отображаются данные с веб-сайта, в отличие от полной загрузки до правильной даты для файла Excell). Поэтому я вставил в цикл команду cout, чтобы попытаться отладить и вуаля, она работала правильно!

Так почему использование функции cout изменяет функцию программы? Есть идеи? Ниже приведен код. (Я нашел два связанных поста, но все еще не могу понять, например, «Можно ли каким-то образом изменить переменные?» И «Странная ошибка в программе C ++: удаление программы разрывов распечатки»)

#include <string>
#include <iostream>
#include <fstream>
#include <algorithm>
#include <windows.h>
#include <wininet.h>

using namespace std;
int main()
{
    HINTERNET hOpen, hURL;
    LPCWSTR NameProgram = L"Webreader"; // LPCWSTR == Long Pointer to Const Wide String 
    LPCWSTR Website;                    
    char file[101];
    int i;
    string filename;        
    unsigned long read;

    filename = "data.txt";
    ofstream myFile(filename);
    if (! myFile)
    {
        cout < "Error opening file\n";
    }
    if ( !(hOpen = InternetOpen(NameProgram, INTERNET_OPEN_TYPE_PRECONFIG, NULL, NULL, 0 )))
    {
        cerr << "Error in opening internet" << endl;
        return 0;
    }                       
    Website = L"http://ichart.finance.yahoo.com/table.csv?s=MSFT&a=00&b=1&c=2009&d=09&e=22&f=2010&g=d&ignore=.csv";
    hURL = InternetOpenUrl( hOpen, Website, NULL, 0, 0, 0 ); //Need to open the URL
    InternetReadFile(hURL, file, 100, &read);
    file[read] = '\0';
    myFile << file;
    while (read == 100)
    {
        InternetReadFile(hURL, file, 100, &read);
        file[read] = '\0';
        myFile << file;
        cout << file; //If I take this line out, the function terminates early.
    }
    myFile << file;
    InternetCloseHandle(hURL);
    myFile.close();
    return 0;
}

Ответы [ 2 ]

7 голосов
/ 22 октября 2010

У вас есть «Гейзенбаг», который исчезает, когда вы пытаетесь его найти. Не заблуждайтесь, проблема все еще существует, и вам do необходимо ее найти.

первая вещь, которую вы должны сделать, это проверить код возврата InternetReadFile.

Кроме того, вы должны не предполагать, что при успешном чтении будут возвращены полные 100 байтов, даже если их будет еще больше. doco заявляет:

Чтобы обеспечить получение всех данных, приложение должно продолжать вызывать функцию InternetReadFile, пока функция не вернет TRUE и параметр lpdwNumberOfBytesRead не станет равным нулю.

:::

Кроме того, преобразованные строки могут не полностью заполнять буфер, поэтому InternetReadFile может вернуть с меньшим количеством данных в lpBuffer, чем запрошено.

Другими словами, я бы добавил:

BOOL rc;

и поменяйте два:

InternetReadFile(hURL, file, 100, &read);

заявления для:

rc = InternetReadFile(hURL, file, 100, &read);

тогда ваш цикл становится:

while ((!rc) || (read > 0))   // I *think* that's right.
6 голосов
/ 22 октября 2010

Выполнение небольшого количества вывода, вероятно, займет немного времени, в течение которого данные могут поступить из сети, готовые для чтения при следующем вызове InternetReadFile.

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

И если так, то не используйте read == 100 в качестве условия продолжения для вашего цикла.Используйте, например, read > 0.Но проверьте документацию , там должно быть указано, чего ожидать.

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

Приветствия и hth.,

...