2009-05-17 2 views
0

Все, что мне нужно, это strcpy().Как скопировать байт [] в char *?

Я хочу видеть, являются ли первые три байта буфера (байтовый массив) «JMX» как строка.

Это то, что я сделал до сих пор:

char * ddj; 
strcpy(ddj, buffer); //buffer is BYTE[] 
if (strcmp("JMX", ddj) == 0) //check first three chars are "JMX" 
{ 
    buffer += 20; //increase the index with 20 
    size -= 20;  //int 
} 

я получаю исключение на STRCMP линии(). В чем проблема?

Я желаю я пишу это в C# :(

+1

Если вы задали вопрос о том, что вы на самом деле пытались сделать, мы могли бы предоставить вам оптимальный и простой способ C++. Вы в настоящее время используете субоптимальный и, откровенно говоря, неправильный способ C сделать это. – 2009-05-17 17:43:51

+0

Еще раз, когда дело доходит до явного управления памятью, большинство ответов технически неверны. Я считаю, что я считаю, что нужно использовать std :: vector или std:; string. – 2009-05-17 17:52:59

ответ

8

Тхо дела идут плохо здесь:

  1. ddj не указывает на какой-либо фактической памяти. Следовательно, копия будет иметь неопределенное поведение.
  2. В первую очередь, копирование не требуется.

Это то, что вы можете сделать:

if(strncmp("JMX", buffer, 3) == 0) { 
    buffer += 20; 
    size -= 20; 
} 

Это использует strncmp вместо strcmp, обеспечивая таким образом, что не более чем три байта не сравниваются. Если buffer может содержать менее чем три байта, вы должны сделать что-то вроде:

if(buf_len >= 3 && strncmp("JMX", buffer, 3) == 0) { 
    buffer += 20; 
    size -= 20; 
} 
2

Вы не выделенной памяти для DDJ. Выделение памяти с использованием новой для него. Например

char *ddj = new char[size]; //Allocate size number of chars 
//do the required comaprisons 

delete[] ddj; //Remember to release the memory. 

С другой стороны, вы можете использовать зЬй :: строку, которая является стандартным классом строка

0

Это UB, потому что ddj не указывает на что Вам нужно выделить память:..

char* ddj = new char[strlen(buffer) + 1]; 

Обязательно укажите delete выделенную вами память, используя delete[] (не указано delete!).

Вы также можете использовать std::string, который, как правило, безопасен, так как вам не нужно иметь дело с указателями и аллюминацией памяти.

Однако, глядя на ваш код, ddj кажется бесполезным. Просто используйте buffer:

if (strcmp("JMX", buffer) == 0) //check first three chars are "JMX" 
{ 
    buffer += 20; //increase the index with 20 
    size -= 20;  //int 
} 
+0

strlen (buffer) + 1 – 2009-05-17 17:42:14

+0

@Neil, Спасибо за исправление. – strager

2

Вы должны выделить новую память для ddj. Либо объявить его как

char ddj[NAX_LENGTH]; 

или с динамическим распределением

char* ddj = new char[length]; // You must use delete[] to free the memory in the end. 

Более удобной альтернативой является std::string.

0

Если вы хотите использовать strcmp ddj, вы также можете сделать это на буфере сначала и сделать копию буфера, если вам это нужно позже.

6

Вы не производите выделение памяти для ddj. Поскольку это локальная переменная, она выделяется в стеке. Локальные переменные по умолчанию не инициализируются до 0/false/NULL, поэтому значение ddj сразу же после его объявления не определено - оно будет иметь значение того, что осталось в памяти в этом конкретном месте в стеке. Любая попытка разыменовать его (то есть читать или записывать память, в которой он указывает) будет иметь неопределенное поведение. В вашем случае это сбой, потому что это указывает на неверный адрес.

Чтобы устранить проблему, вам необходимо выделить хранилище для ddj. Вы можете либо выделить статическое хранилище в стеке, либо динамическое хранилище в куче. Для выделения статической памяти, сделайте следующее:

// Allocate 64 bytes for ddj. It will automatically be deallocated when the function 
// returns. Be careful of buffer overflows! 
char ddj[64]; 

Чтобы выделить динамическую память:

// Allocate 64 bytes for ddj. It will NOT be automatically deallocated -- you must 
// explicitly deallocate it yourself at some point in the future when you're done 
// with it. Be careful of buffer overflows! 
char *ddj = new char[64]; 
... 
delete [] ddj; // Deallocate it 

Вместо управления хранением себя, было бы лучше использовать std::string, которая автоматически занимается управлением памятью.

Наконец, поскольку все, что вы делаете, сравнивает первые три символа строки, нет необходимости перепрыгивать через обруч, чтобы скопировать строку и сравнить ее. Просто используйте strncmp():

if(strncmp(buffer, "JMX", 3) == 0) 
{ 
    ... 
} 
1

Во-первых, это сбой, потому что ddj не указывает ни на что.

Во-вторых, вам не нужно копировать данные с байта [] в char * (они по сути то же самое). Вы можете просто:

if (strncmp("JMX", reinterpret_cast<char*>(buffer), 3) == 0) 
{ 
    // Strings are equal, do what you want 
} 
+0

Для встроенных типов «static_cast» будет работать только с указателями, где неявное преобразование будет работать в любом случае. Вероятно, вы должны изменить это на «reinterpret_cast». –

+0

Да, хорошее место. благодаря –

0

Вы получаете исключение, потому что переменная 'ddj' не инициализируется. Он указывает на мусор, поэтому кто знает, где вы копируете эту строку ...

Вам не нужно копировать байты перед их сравнением.

if(strncmp("JMX", buffer, 3) == 0) // check if the first three characters are "JMX" 
{ 
    buffer += 20; 
    size -= 20; 
} 
Смежные вопросы