2013-07-23 2 views
-1

я есть буферкак прочитать определенную строку из буфера

char buffer[size]; 

, который я использую для хранения содержимого файла из потока (предположим pStream здесь)

HRESULT hr = pStream->Read(buffer, size, &cbRead); 

теперь у меня есть все содержимое этого потока в буфере, размер которого (предположим, размер здесь). Теперь я знаю, что у меня есть две строки

"<!doctortype html" and ".html>" 

которые присутствуют где-то (мы не их loctions) внутри сохраненными содержимое этого буфера, и я хочу сохранить только содержимое буфера от места

"<!doctortype html" to another string ".html>" 

в другой буфер2 [размерWeDontKnow] еще.

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

ответ

1

Вы можете использовать функцию strnstr, чтобы найти нужную позицию в своем буфере. После того, как вы найдете начальный и конечный теги, вы можете извлечь текст inbetween с помощью strncpy или использовать его на месте, если производительность является проблемой.
Вы можете рассчитать необходимый размер с позиций меток и длины первого тега
nLength = nPosEnd - nPosStart - nStartTagLength

+0

действительно ли Visual C++ поддерживает функцию strnstr, если у вас есть какая-нибудь идея ??? и что такое nStartTagLength? поскольку i uderstand you nLength - это размер общего содержимого html и nPosStart = "", нам просто нужно, чтобы вы использовали nStartTagLength ??? – Sss

+0

visual C++ не имеет strnstr, но если вы не уверены, что функция Read дает вам строку с нулевым завершением, вы можете сами положить в нее нуль терминала: 'char buffer [size + 1]; ZeroMemory (буфер, размер + 1); ' nPosStart и nPosEnd являются позициями начального тега" ". nStartTagLength - это длина «

+0

Знаете ли вы, что эквивалентная функция для визуального C++? и вы думаете, что я могу его использовать, используя strtok() здесь? - в то время как (пч! = NULL) { пч = strtok (NULL, "doctortype HTML!" возврат 0; } может я получить позицию "doctortype HTML!" С помощью этого – Sss

0

Ищите парсеры HTML для C/C++.

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

+0

Я проникся во вторую идею, но не могли бы вы рассказать мне, что, делая указатель на символ с начала, я могу сравнить только один символ за раз, но мне нужно сравнить полную строку, которая имеет размер, равный размеру из ** " Sss

+0

'& buffer' - указатель на буферную область. Теперь создайте еще один указатель char как 'char * b = & buffer'. Теперь b указывает на начало буфера, и вы можете перемещать его вокруг и не потерять свой буфер. Теперь, если первый символ в вашем буфере равен '<', тогда '* b' является '<'. Продолжайте увеличивать b, и вы можете читать по одному символу за раз. Теперь продолжайте сравнивать с нужной строкой, и у вас есть то, что вы хотите. –

0

Вы ограничены C, или можете использовать C++?

В справочнике библиотеки C Есть много полезных способов tokenising строк и сравнения для матчей (string.h):

http://www.cplusplus.com/reference/cstring/

Использование C++ Я хотел бы сделать следующее (с использованием буфера и размера переменных из вашего кода):

// copy char array to std::string 
    std::string text(buffer, buffer + size); 

    // define what we're looking for 
    std::string begin_text("<!doctortype html"); 
    std::string end_text(".html>"); 

    // find the start and end of the text we need to extract 
    size_t begin_pos = text.find(begin_text) + begin_text.length(); 
    size_t end_pos = text.find(end_text); 

    // create a substring from the positions 
    std::string extract = text.substr(begin_pos,end_pos); 

    // test that we got the extract 
    std::cout << extract << std::endl; 

Если вам нужна совместимость строки C вы можете использовать:

char* tmp = extract.c_str(); 
+0

Я использую visual C++. вы думаете, что strtok хорош для меня, потому что я должен искать местоположение «», а затем сохранять содержимое между ними. Что ты предлагаешь ? – Sss

+0

Я обновил свой ответ на примере C++, который я тестировал с помощью g ++-компилятора: g ++ (GCC) 4.4.7 20120313 (Red Hat 4.4.7-3). Дайте мне знать, если это сработает для вас. –

+0

@Simson Я сделал это 24 июля. Теперь его более 2 недель. – Sss

0

Если это единственная операция, которая работает на HTML код в вашем приложении, то вы можете использовать решение, которое я приведенную ниже (вы также можете проверить его онлайн - here). Однако, если вы собираетесь сделать более сложный синтаксический анализ, я предлагаю использовать некоторую внешнюю библиотеку.

#include <iostream> 
#include <cstdio> 
#include <cstring> 

using namespace std; 

int main() 
{ 
    const char* beforePrefix = "asdfasdfasdfasdf"; 
    const char* prefix = "<!doctortype html"; 
    const char* suffix = ".html>"; 
    const char* postSuffix = "asdasdasd"; 

    unsigned size = 1024; 
    char buf[size]; 
    sprintf(buf, "%s%sTHE STRING YOU WANT TO GET%s%s", beforePrefix, prefix, suffix, postSuffix); 

    cout << "Before: " << buf << endl; 

    const char* firstOccurenceOfPrefixPtr = strstr(buf, prefix); 
    const char* firstOccurenceOfSuffixPtr = strstr(buf, suffix); 

    if (firstOccurenceOfPrefixPtr && firstOccurenceOfSuffixPtr) 
    { 
     unsigned textLen = (unsigned)(firstOccurenceOfSuffixPtr - firstOccurenceOfPrefixPtr - strlen(prefix)); 
     char newBuf[size]; 
     strncpy(newBuf, firstOccurenceOfPrefixPtr + strlen(prefix), textLen); 
     newBuf[textLen] = 0; 

     cout << "After: " << newBuf << endl; 
    } 

    return 0; 
} 

EDIT я получаю сейчас :). Вы должны использовать strstr, чтобы найти первое появление prefix. Я редактировал код выше и обновлял link.

+0

, не зная места расположения префикса и суффикса, я не могу получить данные между ними, поэтому «THE STRING YOU WANT GET» невозможно, я думаю, вы все еще не могли отказаться и мой вопрос. – Sss

+0

Да, вы правы, я пропустил эту деталь. Я только что обновил ответ :) – podkova

+0

, так что у вас есть идея получить местоположение на Visual C++ ?? в cwe может делать, используя strnstr, но не здесь. – Sss

Смежные вопросы