Task: to implement a Phone book management in C
What I did not understand exactly: I have to implement qsort to sort the phone book (lexicographically by last name and first name) which didnĀ“t work although I used the syntax exactly as it is displayed on the web page: https://www.tutorialspoint.com/c_standard_library/c_function_qsort.htm
The error message:
c:41:25: error: expected ')' before numeric constant
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
typedef struct {
char* vorname;
char* nachname;
char* telefonnummer;
} telefonbucheintrag;
void schreibe_eintrag(
telefonbucheintrag* eintrag_ptr,
char* vorname,
char* nachname,
char* telefonnummer)
{
eintrag_ptr->vorname = malloc(strlen(vorname)+1);
eintrag_ptr->nachname = malloc(strlen(nachname)+1);
eintrag_ptr->telefonnummer= malloc(strlen(telefonnummer)+1);
strcpy(eintrag_ptr->vorname, vorname);
strcpy(eintrag_ptr->nachname, nachname);
strcpy(eintrag_ptr->telefonnummer, telefonnummer);
}
int main()
{
telefonbucheintrag telefonbuch[100];
int32_t telefonbucheintraege = 0;
schreibe_eintrag(telefonbuch+0, "Ada", "Lovelace", "004917155669988");
schreibe_eintrag(telefonbuch+1, "Alan", "Turing", "004917155669922");
schreibe_eintrag(telefonbuch+2, "Ingo", "Mueller", "004917155669911");
schreibe_eintrag(telefonbuch+3, "Ilse", "Mueller", "004917155669933");
schreibe_eintrag(telefonbuch+4, "Stefan", "Sadat", "004917155669988");
telefonbucheintraege = 5;
qsort (telefonbuch, 5, sizeof(int), telefonbucheintraege );
}
replace sizeof(int) with sizeof(*telefonbuch) or what you have
How can I transform from string to LPWSTR
String^ str= "hello world";
LPWSTR apppath= (LPWSTR)(Marshal::StringToHGlobalAnsi(str).ToPointer());
But it doesn't work.After transformed:
You're trying to read single-byte characters (that's what Marshal::StringToHGlobalAnsi is returning) as wide characters (that's what an LPWSTR type points to), and you're getting whatever is in memory interpreted as a wide-character string.
You need to marshal the appropriate type, and you need to be aware of the lifetime of the result. Here's an example program that shows one way to do it, modified from the MSDN example in marshal_context::marshal_as:
// compile with: /clr
#include <stdlib.h>
#include <stdio.h>
#include <string.h>
#include <msclr\marshal.h>
using namespace System;
using namespace msclr::interop;
int main() {
marshal_context^ context = gcnew marshal_context();
String^ str = "hello world";
LPWSTR apppath = const_cast<wchar_t*>(context->marshal_as<const wchar_t*>(str));
wprintf(L"%s\n", apppath);
delete context;
return 0;
}
Note that a reference to apppath is likely to be bogus after the deletion of context.
I've commandLine arguments in a C++/CLI program denoted by char* argv[].
I want to transfer all the contents getting concatenated to a String^ class.
Code:
String ^masterString = "Commands=>";
for(int i=0; argv[i] != nullptr; ++i)
masterString += String(argv[i]);
However, I find the above not working in the last statement where I use += operator.
What's the wrong usage here? Error here is No operators match the operands.
Any other better ways to store contents into String^ from char*?
Look into MSDN, mostly into this:
#include <stdlib.h>
#include <string.h>
#include <msclr\marshal.h>
using namespace System;
using namespace msclr::interop;
int main() {
const char* message = "Test String to Marshal";
String^ result;
result = marshal_as<String^>( message );
return 0;
}
btw: I didn't check this. Just googled it. But, I think, this would work, cause it posted in MSDN.
The question is in the title. Need help figuring out why my code compiles but doesn't work as intended. Thanks!
//This example demonstrates how to do vector<string> to vectro<int> conversion using a function.
#include <iostream>
#include <string>
#include <vector>
#include <sstream>
using namespace std;
vector<int>* convertStringVectorToIntVector (vector<string> *vectorOfStrings)
{
vector<int> *vectorOfIntegers = new vector<int>;
int x;
for (int i=0; i<vectorOfStrings->size(); i++)
{
stringstream str(vectorOfStrings->at(i));
str >> x;
vectorOfIntegers->push_back(x);
}
return vectorOfIntegers;
}
int main(int argc, char* argv[]) {
//Initialize test vector to use for conversion
vector<string> *vectorOfStringTypes = new vector<string>();
vectorOfStringTypes->push_back("1");
vectorOfStringTypes->push_back("10");
vectorOfStringTypes->push_back("100");
delete vectorOfStringTypes;
//Initialize target vector to store conversion result
vector<int> *vectorOfIntTypes;
vectorOfIntTypes = convertStringVectorToIntVector(vectorOfStringTypes);
//Test if conversion is successful and the new vector is open for manipulation
int sum = 0;
for (int i=0; i<vectorOfIntTypes->size(); i++)
{
sum+=vectorOfIntTypes->at(i);
cout<<sum<<endl;
}
delete vectorOfIntTypes;
cin.get();
return 0;
}
The code above has only one problem: You are deleting your vectorOfStringTypes before you pass it to your conversion function.
Move the line delete vectorOfStringTypes; to after you have called your convert function and the program works as intended.
Can someone please post a simple code that would convert,
System::String^
To,
C++ std::string
I.e., I just want to assign the value of,
String^ originalString;
To,
std::string newString;
Don't roll your own, use these handy (and extensible) wrappers provided by Microsoft.
For example:
#include <msclr\marshal_cppstd.h>
System::String^ managed = "test";
std::string unmanaged = msclr::interop::marshal_as<std::string>(managed);
You can easily do this as follows
#include <msclr/marshal_cppstd.h>
System::String^ xyz="Hi boys";
std::string converted_xyz=msclr::interop::marshal_as< std::string >( xyz);
Check out System::Runtime::InteropServices::Marshal::StringToCoTaskMemUni() and its friends.
Sorry can't post code now; I don't have VS on this machine to check it compiles before posting.
This worked for me:
#include <stdlib.h>
#include <string.h>
#include <msclr\marshal_cppstd.h>
//..
using namespace msclr::interop;
//..
System::String^ clrString = (TextoDeBoton);
std::string stdString = marshal_as<std::string>(clrString); //String^ to std
//System::String^ myString = marshal_as<System::String^>(MyBasicStirng); //std to String^
prueba.CopyInfo(stdString); //MyMethod
//..
//Where: String^ = TextoDeBoton;
//and stdString is a "normal" string;
Here are some conversion routines I wrote many years ago for a c++/cli project, they should still work.
void StringToStlWString ( System::String const^ s, std::wstring& os)
{
String^ string = const_cast<String^>(s);
const wchar_t* chars = reinterpret_cast<const wchar_t*>((Marshal::StringToHGlobalUni(string)).ToPointer());
os = chars;
Marshal::FreeHGlobal(IntPtr((void*)chars));
}
System::String^ StlWStringToString (std::wstring const& os) {
String^ str = gcnew String(os.c_str());
//String^ str = gcnew String("");
return str;
}
System::String^ WPtrToString(wchar_t const* pData, int length) {
if (length == 0) {
//use null termination
length = wcslen(pData);
if (length == 0) {
System::String^ ret = "";
return ret;
}
}
System::IntPtr bfr = System::IntPtr(const_cast<wchar_t*>(pData));
System::String^ ret = System::Runtime::InteropServices::Marshal::PtrToStringUni(bfr, length);
return ret;
}
void Utf8ToStlWString(char const* pUtfString, std::wstring& stlString) {
//wchar_t* pString;
MAKE_WIDEPTR_FROMUTF8(pString, pUtfString);
stlString = pString;
}
void Utf8ToStlWStringN(char const* pUtfString, std::wstring& stlString, ULONG length) {
//wchar_t* pString;
MAKE_WIDEPTR_FROMUTF8N(pString, pUtfString, length);
stlString = pString;
}
I found an easy way to get a std::string from a String^ is to use sprintf().
char cStr[50] = { 0 };
String^ clrString = "Hello";
if (clrString->Length < sizeof(cStr))
sprintf(cStr, "%s", clrString);
std::string stlString(cStr);
No need to call the Marshal functions!
UPDATE Thanks to Eric, I've modified the sample code to check for the size of the input string to prevent buffer overflow.
I spent hours trying to convert a windows form listbox ToString value to a standard string so that I could use it with fstream to output to a txt file. My Visual Studio didn't come with marshal header files which several answers I found said to use. After so much trial and error I finally found a solution to the problem that just uses System::Runtime::InteropServices:
void MarshalString ( String ^ s, string& os ) {
using namespace Runtime::InteropServices;
const char* chars =
(const char*)(Marshal::StringToHGlobalAnsi(s)).ToPointer();
os = chars;
Marshal::FreeHGlobal(IntPtr((void*)chars));
}
//this is the code to use the function:
scheduleBox->SetSelected(0,true);
string a = "test";
String ^ c = gcnew String(scheduleBox->SelectedItem->ToString());
MarshalString(c, a);
filestream << a;
And here is the MSDN page with the example:
http://msdn.microsoft.com/en-us/library/1b4az623(v=vs.80).aspx
I know it's a pretty simple solution but this took me HOURS of troubleshooting and visiting several forums to finally find something that worked.
C# uses the UTF16 format for its strings.
So, besides just converting the types, you should also be conscious about the string's actual format.
When compiling for Multi-byte Character set Visual Studio and the Win API assumes UTF8 (Actually windows encoding which is Windows-28591 ).
When compiling for Unicode Character set Visual studio and the Win API assume UTF16.
So, you must convert the string from UTF16 to UTF8 format as well, and not just convert to std::string.
This will become necessary when working with multi-character formats like some non-latin languages.
The idea is to decide that std::wstring always represents UTF16.
And std::string always represents UTF8.
This isn't enforced by the compiler, it's more of a good policy to have.
#include "stdafx.h"
#include <string>
#include <codecvt>
#include <msclr\marshal_cppstd.h>
using namespace System;
int main(array<System::String ^> ^args)
{
System::String^ managedString = "test";
msclr::interop::marshal_context context;
//Actual format is UTF16, so represent as wstring
std::wstring utf16NativeString = context.marshal_as<std::wstring>(managedString);
//C++11 format converter
std::wstring_convert<std::codecvt_utf8_utf16<wchar_t>> convert;
//convert to UTF8 and std::string
std::string utf8NativeString = convert.to_bytes(utf16NativeString);
return 0;
}
Or have it in a more compact syntax:
int main(array<System::String ^> ^args)
{
System::String^ managedString = "test";
msclr::interop::marshal_context context;
std::wstring_convert<std::codecvt_utf8_utf16<wchar_t>> convert;
std::string utf8NativeString = convert.to_bytes(context.marshal_as<std::wstring>(managedString));
return 0;
}
I like to stay away from the marshaller.
Using CString newString(originalString);
Seems much cleaner and faster to me. No need to worry about creating and deleting a context.
// I used VS2012 to write below code-- convert_system_string to Standard_Sting
#include "stdafx.h"
#include <iostream>
#include <string>
using namespace System;
using namespace Runtime::InteropServices;
void MarshalString ( String^ s, std::string& outputstring )
{
const char* kPtoC = (const char*) (Marshal::StringToHGlobalAnsi(s)).ToPointer();
outputstring = kPtoC;
Marshal::FreeHGlobal(IntPtr((void*)kPtoC));
}
int _tmain(int argc, _TCHAR* argv[])
{
std::string strNativeString;
String ^ strManagedString = "Temp";
MarshalString(strManagedString, strNativeString);
std::cout << strNativeString << std::endl;
return 0;
}
For me, I was getting an error with some of these messages. I have an std::string. To convert it to String^, I had to do the following String^ sysString = gcnew String(stdStr.c_str()); where sysString is a System::String^ and stdStr is an std::string. Hope this helps someone
You may have to #include <string> for this to work