sprintf
작업에서 얻은 문자열의 길이를 예상해야합니다. 어떻게해야합니까? 즉, 아래 코드에서 값 50
을 harcoding하지 않는 방법은 무엇입니까?sprintf 결과 길이 추정
double sum;
char* resultString;
..
resultString = new char[50]; //how can I avoid hardcoding 50 here?
sprintf(resultString,"[%e]",sum);
sprintf
작업에서 얻은 문자열의 길이를 예상해야합니다. 어떻게해야합니까? 즉, 아래 코드에서 값 50
을 harcoding하지 않는 방법은 무엇입니까?sprintf 결과 길이 추정
double sum;
char* resultString;
..
resultString = new char[50]; //how can I avoid hardcoding 50 here?
sprintf(resultString,"[%e]",sum);
snprintf(char *buffer, int buf_size, const char *format, ...);
을 사용하십시오. sprintf
은 안전하지 않습니다.
그러나 나는 당신이 C++를 사용하는 읽기, 그래서 나는이 같은 이제 stringstream을 사용합니다 :
#include <iostream>
#include <sstream>
double sum;
std::stringstream buf(std::stringstream::in | std::stringstream::out);
std::string resultString;
..
buf << "[" << std::scientific << sum << "]";
resultString = buf.str();
적절한 방법의 sprintf를 사용하지 않습니다. C++ (표준 iostreams 기능을 포함하되 이에 국한되지 않음)에서 출력을 형식화하기위한 확장 가능하고 안전한 많은 방법이 있습니다. C로 코딩하면 snprintf를 사용하십시오.
가장 좋은 방법은이 모든 대신 std::stringstream
사용하는 것 피하기 위해 :
std::stringstream buffer;
buffer << std::scientific << sum;
std::string resultString = buffer.str();
snprintf
은 버퍼가 충분히 크다 경우 기록 된 것입니다 문자의 수를 반환합니다. 두 번 호출 할 수 있습니다. 길이를 얻으려면 한 번, 문자열을 실제로 포맷하려면 다시 호출하십시오.
좋은 빠른 방법은 snprintf
의 고정 크기 버퍼를 사용하는 것입니다.이 버퍼는 버퍼가 충분히 클 경우 인쇄 할 문자 수를 반환합니다. 그 반환 값이 버퍼가 충분히 크지 않다는 것을 나타내는 경우, 현재 알려진 크기의 malloc()
또는 new를 사용하십시오. 더 느리지 만 간단한 대안은 항상 힙에서 할당 한 asprintf()
을 찾는 것입니다. 몇 줄에 위에 자신의 asprintf()
을 구현할 수 있습니다.
printf와 같은 기능을 사용하는 동안 각 번호에 길이를 제공하는 옵션이 있습니다.
printf ("% .2s", "12345");
이 예제는 처음 두 문자 만 인쇄합니다. 이렇게하면 필요한 최대 크기를 예측/제한 할 수 있습니다.
그렇지 않으면 표준을 사용하여 다른 사람
보통에 의해 제안 많은 좋은 답변이 있습니다 :: 이제 stringstream가 정답이다. 아직 C 코드를 인터페이싱 할 때 printf (fmt, ...)를 사용해야하므로 std :: stringstream을 사용할 수 없습니다. 이러한 경우 하나는 여전히 같은 가변 길이 문자열을 포맷 할 수 있습니다 :
static void append_format(std::string& s, const char* format, va_list vl)
{
auto cur_length = s.length();
auto sz = vsnprintf(NULL, 0, format, vl);
s.resize(cur_length + sz);
auto sz2 = vsnprintf(&s[cur_length], sz + 1, format, vl);
assert(sz2 == sz);
}
static void example_usage()
{
std::string s;
append_format(s, "%s %dD world", "hello", 3); // s == "hello 3D world"
append_format(s, ", PI= ~%f", 3.14); // s == "hello 3D world, PI= ~3.14"
std::cout << s;
}
메모를, printf와 그 클론 안전 입력하지 않기 때문에이 방법은 안전 입력되지 않았는지 확인합니다. 하지만 결과 문자열이 얼마나 오랫동안 유효한지에 관계없이 유효한 호출에 대한 버퍼 오버런이 발생하지 않습니다
왜 C++ 대신'string'을 사용합니까? –
참고로,'[someInitializedIntVariable]'인덱스에서 변수를 보낼 수도 있습니다. – Mahesh