copy char*

G

Gary Wessle

string a = "abcdef";
aa[80] = a.c_str();

bb[40] = how can I get def from aa in here?

thanks
 
O

ondra.holub

Gary Wessle napsal:
string a = "abcdef";
aa[80] = a.c_str();

bb[40] = how can I get def from aa in here?

thanks

a.c_str() + 4

But you should know, that result of c_str() method is valid only till
the first change in `a'. So you should make copy of i if you need
C-string and cannot guarantee, that no change in `a' will occure.
 
S

SirMike

Dnia 15 Nov 2006 22:43:39 +1100, Gary Wessle napisa³(a):
string a = "abcdef";
aa[80] = a.c_str();

bb[40] = how can I get def from aa in here?

use strncpy
 
G

Gary Wessle

SirMike said:
Dnia 15 Nov 2006 22:43:39 +1100, Gary Wessle napisał(a):
string a = "abcdef";
aa[80] = a.c_str();

bb[40] = how can I get def from aa in here?

use strncpy

void func1(const char* p){
char frst[40];
char last[40];
strncpy(frst, p, 3); //first 3 ????
strncpy(last, p, 3); //last 3 ?????
}

string a = "abcdef";
func1(a.c_str());
 
J

Jim Langston

Gary Wessle said:
SirMike said:
Dnia 15 Nov 2006 22:43:39 +1100, Gary Wessle napisal(a):
string a = "abcdef";
aa[80] = a.c_str();

bb[40] = how can I get def from aa in here?

use strncpy

void func1(const char* p){
char frst[40];
char last[40];
strncpy(frst, p, 3); //first 3 ????
strncpy(last, p, 3); //last 3 ?????
}

string a = "abcdef";
func1(a.c_str());

void func1( const char* p )
{
char first[40];
char last[40];
strncpy( first, p, 3 );
strncpy( last, p + 3, 3 );
}

Ugly code. Prefer std::string instead.

void func1( const std::string Value )
{
std::string first = Value.substr( 0, 3 );
std::string last = Value.substr( 4, 3 );
}
 
B

BobR

Gary Wessle wrote in message ...
SirMike said:
use strncpy

void func1(const char* p){
char frst[40];
char last[40];
strncpy(frst, p, 3); //first 3 ????
strncpy(last, p, 3); //last 3 ?????
}

string a = "abcdef";
func1(a.c_str());

void func1( char const *p, std::eek:stream &out ){
char frst[ 40 ];
char last[ 40 ];
strncpy( frst, p, 3 ); //first 3 ????
strncpy( last, p+3, 3 ); //last 3 ?????
out << "frst="<<frst<<" last="<<last<<std::endl;
return;
}

{
std::string a = "abcdef";
func1( a.c_str(), std::cout );
}
// out: frst=abc last=def
 
D

Default User

BobR said:
void func1( char const *p, std::eek:stream &out ){
char frst[ 40 ];
char last[ 40 ];
strncpy( frst, p, 3 ); //first 3 ????
strncpy( last, p+3, 3 ); //last 3 ?????
out << "frst="<<frst<<" last="<<last<<std::endl;
return;
}

{
std::string a = "abcdef";
func1( a.c_str(), std::cout );
}
// out: frst=abc last=def


Did you actually try this? If you got the purported results, then it
was by sheer bad luck. You didn't terminate the string, and strncpy
doesn't do it for you. Outputting the result was undefined behavior.




Brian
 
G

Gary Wessle

#include <string>
#include <iostream>
using namespace std;

class myType {
protected:
char _frst[40];
char _second[40];
char _pair[80];
public:
const char* frst() const;
const char* second() const;
myType(const char* pair);
};

myType::myType(const char* pair)
{
strncpy(_frst, pair, 3);
strncpy(_second, pair+4, 3);
}
const char* myType::frst()const {return _frst;}
const char* myType::second()const {return _second;}

int main(){
string s = "abc-def";
myType mt(s.c_str());
string tmp = mt.frst();
string tmp2 = mt.second();
cout << tmp << " " << tmp2 << endl;
}

//output
abcMh Q%G.ANoN?N=NoN?N=NoN?N=NoN?N=%@`%G.ANoN?N=%@M$B'\(B$B%G.ANoN?N=(B$B%@(B def
 
G

Gary Wessle

I need it to ouput
abc def

what must be done to
strncpy(_frst, pair, 3);
strncpy(_second, pair+4, 3);
in the c'tor?
 
B

BobR

Default User wrote in message said:
BobR wrote:


Did you actually try this?
Yes.

If you got the purported results, then it
was by sheer bad luck. You didn't terminate the string, and strncpy
doesn't do it for you. Outputting the result was undefined behavior.

Of course you are correct. My bad. (gads, I hate that phrase!!).
Thanks for the 'heads-up'.

<?>
It must have been that the char arrays were initialized to zeros by my
compiler.
<checking....>
Nope!!! Just happened to be a zero at 4th position in both arrays.
[....even on re-compiles. ....and adding another array before those.]
[ I can't seem to break it! ]
</?>

Murphy's "bad luck" clause strikes again!!

Thanks again for the correction.
 
B

BobR

Default User wrote in message said:
BobR wrote:

Outputting the result was undefined behavior.

[ ref: the missing terminator. ]

HEY! How come why for you yell at me but not Jim?
<G>
 
G

Gary Wessle

in order to get the clean output "abd def" I did some changes to the
code but now getting Seg Fault.

#include <string>
#include <iostream>
using namespace std;

class myType {
protected:
char _frst[40];
char _second[40];
char _pair[80];
public:
const char* frst() const;
const char* second() const;
myType(const char* pair);
};

myType::myType(const char* pair)
{
strncpy(_frst, pair, 3);
strncpy(_second, pair+4, 3);
}
const char* myType::frst()const {
char* r;
strncpy(r,_frst,3);
return r;}
const char* myType::second()const {
char* r;
strncpy(r,_second,3);
return r;
}

int main(){
string s = "abc-def";
myType mt(s.c_str());
cout << mt.frst() << " " << mt.second() << endl;
}
 
B

BobR

Gary Wessle wrote in message ...
#include <string>
#include <iostream>
using namespace std;

class myType { protected:
char _frst[40];
char _second[40];
char _pair[80];
public:
const char* frst() const;
const char* second() const;
myType(const char* pair);
};

myType::myType(const char* pair){
strncpy(_frst, pair, 3);

// Like Default User pointed out, I forgot to terminate the array:
_frst[4] = '\0';
strncpy(_second, pair+4, 3);

_second[4] = '\0';

// or:
// frst[4]= 0;
// second[4]= 0;

// also, BAD nameing.
// Put the underscore on the end (not the begin) of the names
// if you MUST use them.
}
const char* myType::frst()const {return _frst;}
const char* myType::second()const {return _second;}

int main(){
string s = "abc-def";

// You changed the spec on us!
// I'll let you figure out the 'fix' as punishment.
myType mt(s.c_str());
string tmp = mt.frst();
string tmp2 = mt.second();
cout << tmp << " " << tmp2 << endl;
}

//output
abcMh
Q%G.ANoN?N=NoN?N=NoN?N=NoN?N=%@`%G.ANoN?N=%@M$B'\(B$
B%G.ANoN?N=(B$B%@(B def

You were luckier than I was!! <G>
 
B

BobR

Gary Wessle wrote in message ...
in order to get the clean output "abd def" I did some changes to the
code but now getting Seg Fault.

#include <string>
#include <iostream>
using namespace std;

class myType {
protected:
char _frst[40];
char _second[40];
char _pair[80];
public:
const char* frst() const;
const char* second() const;
myType(const char* pair);
};

myType::myType(const char* pair){
strncpy(_frst, pair, 3); _frst[ 4 ] = 0;
strncpy(_second, pair+4, 3); _second[ 4 ] = 0;
}
const char* myType::frst()const {
char* r;

OK, when working with raw arrays, you always need to ask yourself, "Is there
enough room in there?".
You declared 'r' as a pointer to type 'char', but, where is the storage for
the 'strncpy' to copy to? You need to make some storage, and then put the
address of that into 'r'.
You are getting the 'Seg Fault' because you did not point 'r' to anything, or
initialize it. It's pointing to something that is not yours to change.

Now before you get the idea to do:

char *r( new char[ 40 ] );

....remember that now you are putting the life of that pointed to storage in
the callers hands, it's up to them to see that it is eventually
'delete[]'ed!!
Hint: 'cout' don't know how to fo that!
The easy fix is to dump the 'strncpy' and 'char*' here, and just do:

return _frst;


// > strncpy(r,_frst,3);
// > return r;
}
const char* myType::second()const {
char* r;

Same here.
strncpy(r,_second,3);
return r;
}

int main(){
string s = "abc-def";
myType mt(s.c_str());
cout << mt.frst() << " " << mt.second() << endl;
}

Alf P. Steinbach's "Pointers" document:
http://home.no.net/dubjai/win32cpptut/special/pointers/ch_01.pdf
 
J

Jim Langston

BobR said:
Default User wrote in message said:
BobR wrote:

Outputting the result was undefined behavior.

[ ref: the missing terminator. ]

HEY! How come why for you yell at me but not Jim?
<G>

Because I didn't try to output the result. I just gave the op what he asked
for, abc in the first, cdf in the second. He didn't ask to terminate them,
nor even why he was doing it. Now, if he actually wants to output them, I
would do it a different way. I suggested he use std::string anyway.
 
D

Default User

Old said:
Gary said:
string a = "abcdef";
aa[80] = a.c_str();

This is an error: you can't assign to arrays

But you can to an array element, which is why his missing declarations
for things like aa made the problem insoluable.

If aa were declared something like:

const char *aa[81];

Then you could assign the results from c_str() to that element. Now,
that's apparently not what he was going for.




Brian
 

Ask a Question

Want to reply to this thread or ask your own question?

You'll need to choose a username for the site, which only take a couple of moments. After that, you can post your question and our members will help you out.

Ask a Question

Members online

Forum statistics

Threads
474,430
Messages
2,571,676
Members
48,796
Latest member
Greg L.

Latest Threads

Top