2

以下は私のサンプルコードです。これは、アプリケーションで使用しているコードに似たサンプルです。

#define STR_SIZE 32

void someThirdPartyFunc(const char* someStr);

void getString(int Num, const char* myStr)
{
  char tempStr[] = "MyTempString=";
  int size = strlen(tempStr) + 2;
  snprintf((char*)myStr, size, "%s%d", tempStr, Num);
}

int main()
{
  const char * myStr = new char(STR_SIZE);
  getString(1, myStr); // get the formated string by sending the number
  someThirdPartyFunc(myStr); // send the string to the thirdpartyFunction
  delete myStr;

  return 0;
}

このコードを使用すると例外が発生します。問題は「myStr」の削除にあると思います。しかし、削除は本当に必要です。

getStringで文字列をフォーマットしてThirdPartyFuncに送信する他の方法はありますか?

前もって感謝します。

4

2 に答える 2

9

次の行で、文字の配列ではなく1つの文字を割り当てています。

 const char * myStr = new char(STR_SIZE);

また、割り当てられた1つのcharが値で初期化されるためSTR_SIZE、この場合は「charオーバーフロー」が発生します。

サイズの配列が必要な場合STR_SIZE

 const char * myStr = new char[STR_SIZE];

(長方形[]に注意してください)。delete[]演算子を使用して、そのような割り当てられたメモリのチャンクの割り当てを解除する必要があります。

個人的なメモ:上記で記述したコード(手動で割り当てられた文字列など)は、教育的に優れています。あなたはそのような多くの間違いをするでしょう、そしてそれでC /C++の内部の働きについて学びます。プロダクションコードの場合はそれを望まず、プロダクションコードの場合、std::stringまたは他の文字列コンテナは文字列関連の間違いを繰り返さないようにします。一般に、文字列ライブラリがどのように機能するかをうまく再発明したのはあなたではありません。std::vector同じことが、dynamicly-growable-arrays( )やdictionary-typesなどの他のコンテナタイプにも当てはまります。しかし、上記のコードを教育的にいじるのは良い目的です。

コードスニペットには他の問題があります(関数に渡してからRAMを変更し、呼び出し時にパラメーターをconst char*正しく計算しないなど)が、これらはセグメンテーション違反の問題とは関係ありません。sizesnprintf

于 2013-02-08T06:27:39.580 に答える
5

技術的なものではなく、

const char * myStr = new char(STR_SIZE);

行う

char const myStr[STR_SIZE] = "";

どちらにも文字列を変更できないという問題があることに注意してください。

しかし、あなたは割り当て/割り当て解除の問題についてのみ尋ねました。


しかし、それでは、言語技術より上のレベルでは非常に多くの間違いがあります。

完全な元のコードは次のとおりです。

void someThirdPartyFunc(const char* someStr);

void getString(int Num, const char* myStr)
{
  char tempStr[] = "MyTempString=";
  int size = strlen(tempStr) + 2;
  snprintf((char*)myStr, size, "%s%d", tempStr, Num);
}

int main()
{
  const char * myStr = new char(STR_SIZE);
  getString(1, myStr); // get the formated string by sending the number
  someThirdPartyFunc(myStr); // send the string to the thirdpartyFunction
  delete myStr;

  return 0;
}

C++レベルでこれを行う方法は次のとおりです。

#include <string>           // std::string
#include <sstream>          // std::ostringstream
using namespace std;

void someThirdPartyFunc( char const* ) {}

string getString( int const num )
{
    ostringstream stream;
    stream  << "MyTempString=" << num;
    return stream.str();
}

int main()
{
  someThirdPartyFunc( getString( 1 ).c_str() );
}

より自然なコードから消えました#defineが、すべて大文字のマクロ名であっても、望ましくないテキスト置換に非常に簡単につながる可能性があることに注意してください。そして、すべて大文字で叫ぶことはとにかく目障りです(これが、他の規則とは対照的に、マクロ名の規則である理由です)。C ++では、const代わりに使用してください。

于 2013-02-08T06:26:20.153 に答える