Wie die strncpy_s-Funktion von visual c++?
Ich Lerne einige neue Dinge in C++, und ich war versucht, dies zu testen strncpy_s-Funktion von Visual C++. Jedoch habe ich einige Probleme, da das Programm abstürzt und ich weiß nicht, was Los ist, aber ich bin sicher, es ist ein ziemlich blödes problem. Der source-code ist so etwas wie dieses:
#include "stdafx.h"
#include <iostream>
#include <cstdio>
#include <cstring>
int main()
{
char *p;
p=(char *)malloc(sizeof(char)*strlen("Hello!\n"));
strncpy_s(p,strlen("Hello!\n"),"Hello!\n",strlen("Hello!\n"));
std::cout << p;
std::cout << strlen("Hello!\n") << std::endl;
return 0;
}
Als ich sagte, ich bin nicht mit std::string coz ich will versuchen, diese neue Funktion und wissen, wie es funktioniert.
- Verwenden Sie einen debugger, um zu sehen, wo der crash passiert. Stackoverflow ist nicht ein debugger.
- Das habe ich getan. Das problem war in strncpy_s Aufruf der Funktion.
- Ich kopiere den text schrieb ich in der Frage Thema: "Wie ich schon sagte, ich bin nicht mit std::string coz ich will versuchen, diese neue Funktion und wissen, wie es funktioniert."
- Yep. Aber was ist das problem mit std::cout << p;?
- Auch in C++ gibt es keinen Grund für die Verwendung
strncpy
oder fast jede andere Funktion in dercstring
header. - Als ich sagte, ich wollte versuchen, diese neue Funktion, ich freue mich auf das erlernen neuer Sachen.
- p ist ein Zeiger, die Sie nicht wollen, um die Ausgabe der Zeiger, die Sie wollen, um die Ausgabe der Zeichenfolge, die Sie zeigt. Versuchen
std::cout << &p;
- Ich denke, du hast das rückwärts... dass ein Teil seines code ist in Ordnung, aber Ihr Ersatz druckt den Zeiger.
Du musst angemeldet sein, um einen Kommentar abzugeben.
Ich nehme meine Kommentare zurück, die ich gelesen die Dokumentation mehr gezielt. Ihr code ist die übergabe Ungültiger Parameter, und die Berufung auf das ungültige parameter handler. Vielleicht ist das, was passiert. Nämlich:
Diese Zeile reserviert Zimmer für die 7 Zeichen, welche die Länge der Zeichenfolge, aber nicht genug Platz für eine null-terminator. (Dies ist in der Regel ein Fehler)
In der Dokumentation für
strncpy_s
sagt: Diese Funktionen versuchen zu kopieren, die erste D-Zeichen von strSource nach strDest, wobei D der geringeren Anzahl und der Länge der strSource. , Wenn diese D Zeichen passen in strDest (dessen Größe gegeben ist, wie numberOfElements) und lassen noch Raum für einen null-terminator, dann werden diese Zeichen kopiert und eine abschließende null angehängt wird; sonst, strDest[0] eingestellt ist, um das null-Zeichen und die ungültigen parameter handler wird aufgerufen,, wie beschrieben, im Parameter-Validierung.Sind Sie möglicherweise sehen die "invalid parameter handler"?
Brauchen Sie 1 oder mehrere Zeichen für die Beendigung Charakter (
'\0'
), so dass Sie ersetzen müssenstrlen("Hello!\n")
mitstrlen("Hello!\n") + 1
. Sie speichern könnte diese Länge in einigen Variablen anstelle von aufrufenstrlen
wieder. Auch da man sich mit C++, die Sie nutzen könntennew /delete
stattmalloc /free
:sizeof "Hello!\n"
eher alsstrlen("Hello!\n")+1
. Das funktioniert nur für string-Literale, natürlich.strlen
ist mehr "illustrative" in diesem Fall, da war es die wichtigste Ursache für sein problem.Den 'erhöhter Sicherheit' string-Funktionen sind im wesentlichen entwickelt, um crash, wenn Sie auf ein problem stoßen.
Vom Microsoft docs auf
strncpy_s()
:Den Beschreibung der Parameter Validation ist:
Ihrem Beispiel-Programm bietet einen Puffer, der zu klein ist von einem
char
(es gibt keinen Platz für den null-terminator).So, wenn Sie konkret ändern, was passieren soll, wenn die
strxxxx_s
Funktionen tun, wenn ein Fehler aufgetreten ist, wird Ihr Programm Abstürzen von design. Die Idee ist, dass ein crash ist besser als ein Fehler, der möglicherweise öffnen Sie eine Sicherheitslücke.strlen(s)
nur sagen, die Länge der Zeichenkette, ohne das NULL-terminator. , Speicherplatz reservieren, in denen eine Zeichenfolge kopieren, verwenden Sie in der Regelstrlen(s)+1
hinzufügen, Platz für ein NUL-terminator.strlen(s+1)
, die noch kompiliert, gibt aber eine falsche Antwort (zu klein, um 2 statt 1), aber der Fehler ist noch leichter zu übersehen.Müssen Sie reservieren strlen("Hallo!\n") + 1 (für die null-terminator). Und sizeof(char) ist völlig sinnlos, da sizeof(char) ist garantiert 1 auf allen Plattformen.
char
haben Größe 1. In der Tatsizeof
gibt die Anzahl der chars.Warum bist du mit malloc oder char*, wenn Sie C++?
oder
Aber um auf Ihre ursprüngliche Frage, die Sie wahrscheinlich benötigen, um verwenden
strlen(p) + 1
Und wenn Sie einen char* aus der Zeichenfolge, die Sie verwenden können
p.c_str()