?
Solved

convert character array to string

Posted on 2003-02-25
21
Medium Priority
?
661 Views
Last Modified: 2013-12-03
Hi, I am wondering how to convert a character array to a standard string.

Like:

char buffer[80];
string line;

how to convert the character array buffer to string line?

Thank you very much!
0
Comment
Question by:anxx0018
[X]
Welcome to Experts Exchange

Add your voice to the tech community where 5M+ people just like you are talking about what matters.

  • Help others & share knowledge
  • Earn cash & points
  • Learn & ask questions
  • 5
  • 5
  • 4
  • +3
21 Comments
 
LVL 7

Expert Comment

by:burcarpat
ID: 8021389
use std::string.assign() as in "line.assign(buffer);"
0
 

Expert Comment

by:entropy12
ID: 8021405
you can pass a c-string into the costructor of a string like so:

char buffer[80];
string line(buffer);
0
 
LVL 46

Expert Comment

by:Kent Olsen
ID: 8021507

You can also "set" the String variable to the char variable.


char   buffer[80];
String line;


line = buffer;

caution -- if the text at 'buffer' is not zero byte terminated, 'line' may assume the value of a very long string.


Kdo

0
What does it mean to be "Always On"?

Is your cloud always on? With an Always On cloud you won't have to worry about downtime for maintenance or software application code updates, ensuring that your bottom line isn't affected.

 
LVL 40

Expert Comment

by:Kyle Abrahams
ID: 8022703
strcopy(line, (string)buffer);
0
 

Expert Comment

by:vinay_krishna
ID: 8024726
The Best way to make a string from char array is to pass char array as an argument to the String Constructor. String is nothing but the collection of chars .
Calling Constructor:
 String line = new String( buffer);

 
0
 

Expert Comment

by:entropy12
ID: 8026673
>>The Best way to make a string from char array is to pass >>char array as an argument to the String Constructor. >>String is nothing but the collection of chars .
>>Calling Constructor:
>>String line = new String( buffer);

this forum is for C++, not C#
or else you meant:

*string line = new string(buffer);
0
 

Author Comment

by:anxx0018
ID: 8027804
I feel very strange about the two points below:

1. strcopy can not be identified under linux, although I have included <string> in my header files.
Is it MFC function?
Error:`strcopy' undeclared (first use this function)

2. String line = new string(buffer) does not work. There is always error:
conversion from `std::string*' to non-scalar type `
   std::basic_string<char, std::char_traits<char>, std::allocator<char> >'
   requested


Thanks!
0
 

Expert Comment

by:entropy12
ID: 8028434
he probably meant strcpy not strcopy
also as i said above String line = new string(buffer)
won't work. you need to use:

string * line = new string(buffer);
0
 
LVL 7

Expert Comment

by:burcarpat
ID: 8029071
> "1. strcopy can not be identified under linux, although I have included <string> in my header files."

do not use strcpy unless it is absolutely necessary.  it's a c function and has no place in c++ unless for legacy c api support or for ultimate string performance requirements ( and, even then, there are other alternatives )


> "2. String line = new string(buffer) does not work. There is always error: conversion from `std::string*' to non-scalar type `"

this is also a bad idea ( even if you change "String" to "string*" as suggested, which is the correct syntax, btw).  it kills the purpose of using std::string in the first place.  std::string dynamically allocates and releases its own memory.  why would you want to introduce pointers into that?

...

the first three post, i.e. mine, entropy12's, and Kdo's reflect the correct ways to do this in c++.  the rest is either c and/or do not reflect the c++ philosophy very well ( i.e. avoid pointers as much as possible ).  furthermore, in many stl implementations ( including sgi implementation, which is used by stlport, gcc and borland and considered the standard ) both the constructor and operator= actually internally use assign()
0
 

Author Comment

by:anxx0018
ID: 8037770
Burcarpat,

Can you please help me check why the following program does not go into loop? I really could not understand it!

Thanks a lot!

Program:
#include <stdio.h>
#include <stdlib.h>
#include <fstream>

#include <iostream>
#include <string>
#include <map>

using namespace std;

//Min is to return the smaller value of m1 and m2.
int Min(int m1, int m2)
{
  if (m1<m2)
    return m1;
  else
    return m2;
}

//WordCmp is used to compare two strings, if k1 is alphabetically smaller than k2, return 0; if k1 is bigger than k2, return 1; if k1 and k2 are equal, return 2.

int WordCmp(string k1, string k2)
{
  int len1,len2;

  char *s1 = new char[strlen(k1.c_str()+1)];
  strcpy(s1,k1.c_str());

  char *s2 = new char[strlen(k2.c_str()+1)];
  strcpy(s2,k2.c_str());
 
  int n = Min(strlen(k1.c_str()), strlen(k2.c_str()));
 
   for (int i= 0; i<n; i++)
    {
      if (s1[i]<s2[i])
       {
       return 0;
       break;
       }
      else if (s1[i]>s2[i])
     {      
       return 1;
       break;
     }
    }
   return 2;
}


//This function is to sort names alphabetically. First, delete "END" and "̼ @P" from inflowing stream. Then if read-in is smaller than the first name of the array, put it at the first place and put others larger. If read-in is larger than the biggest one, put it at the end of the array. Otherwise, check where is a good place for the new read-in, and then put it there.

int main()
{
  ifstream source("/tmp_mnt/home/anqian/keywords.txt");
  map<int, string> key_array;

  string str_Line;

  if(!source)
    {
      cerr<<"Error opening the File!"<<endl;
      return 1;
    }

  else
    {
      getline(source,str_Line);
      key_array[0]=str_Line;
      getline(source,str_Line);

      while(!source.eof() && str_Line.compare("END")!=0 && str_Line.compare("̼ @P")!=0)
     {
       if (WordCmp(str_Line,key_array[0])==0)
           {
             cout<<key_array.size()<<endl;
             for (int i = key_array.size(); i<1; i--)
               {
                 cout<<"I am in for loop!"<<endl;
                 key_array[i]=key_array[i-1];
               }
             key_array[0]=str_Line;
             getline(source,str_Line);
           }

            else if(WordCmp(str_Line,key_array[key_array.size()-1])==1)
           {
             key_array[key_array.size()]=str_Line;
             getline(source,str_Line);
           }
           
            else
           {
             for (int i=key_array.size(); i=2; i--)
               {
                 if (WordCmp(key_array[i-1],str_Line)==1 && WordCmp(key_array[i-2],str_Line)==0)
                {
                  cout<<"Yes! I am here"<<endl;
                  for(int j=key_array.size(); j<=i; j--)
                    {
                      key_array[j]=key_array[j-1];
                    }
                  key_array[i-1]=str_Line;
                  break;
                }
               }
           
           getline(source,str_Line);
           }
     }
      return 0;
    }

  for(int k=0; k<key_array.size();k++)
    {
      cout<<key_array[k]<<endl;
    }
}

source file:
SIMPLE  
BITPIX  
NAXIS  
EXTEND  
NEXTEND
DATE    
FILENAME
FILETYPE
TELESCOP
INSTRUME
EQUINOX
ROOTNAME
PRIMESI
TARGNAME
RA_TARG
DEC_TARG
PROPOSID
LINENUM
PR_INV_L
PR_INV_F
PR_INV_M
TDATEOBS
TTIMEOBS
TEXPSTRT
TEXPEND
TEXPTIME
POSTARG1
POSTARG2
OVERFLOW
CAL_VER
PROCTIME
CFSTATUS
OBSTYPE
OBSMODE
PHOTMODE
0
 
LVL 40

Expert Comment

by:Kyle Abrahams
ID: 8046408
>>do not use strcpy unless it is absolutely necessary.  it's a c function and has no place in c++ unless for legacy c api support or for ultimate string performance requirements ( and, even then, there are other alternatives )

I beg to differ.  C++ is absolutely reverse compatible, after all, it was written in C, and is just easier to use than C.  Anything that you can use in C is available to C++. (though it doesn't work going from c++ to c)  strcpy is also taken from the string class, which is a standard c++ class.  instead of using strcpy, you can also use the = operator:

line = buf;  

plain and simple.
0
 
LVL 40

Expert Comment

by:Kyle Abrahams
ID: 8046412
(depending on the compiler, you may have to cast it)

line = (string) buf;
0
 
LVL 7

Expert Comment

by:burcarpat
ID: 8055585
ged325,

> "I beg to differ..."

i would suggest reading stroustrup's book for this, who, as we all know, is the creator of c++.  in his book, he suggests use of std::string and its member functions whenever possible and revert back to c-style functions only if necessary.  many other c++ experts such as herb sutter ( exceptional c++ series ) and scott meyers ( effective c++ series ) would agree

here's a quote from stroustrup, 3rd. ed., page 600 for your convenience:

"Whenever possible, C-style strings are best avoided in favor of strings. C-style strings and their associated standard functions can be used to produce very efficient code, but even experience C and C++ programmers are prone to make uncaught "silly errors" when using them."


> "C++ is absolutely reverse compatible, after all..."

this is not correct.  for a detailed discussion of this issue, please see these below articles,

    http://www.cuj.com/articles/2002/0207/0207d/0207d.htm?topic=reference

    http://www.cuj.com/articles/2002/0208/0208c/0208c.htm?topic=reference

    http://www.cuj.com/articles/2002/0209/0209c/0209c.htm?topic=reference


> "instead of using strcpy, you can also use the = operator: ... line = buf;"

if you check sources for your c++ library ( such as gcc's ), you'll see that in majority of the cases, operator= actually internally uses assign().  in some implementations, operator= is defined differently but i have never seen one that uses strcpy
0
 
LVL 7

Expert Comment

by:burcarpat
ID: 8058753
anxx0018, no offense, but that's really too much code for a 20 points question.  i can give you a couple of tips, though:

- don't use all those char*s at all.  switch fully to std::string

- you don't need WordCmp.  std::lexicographical_compare does that for you

- your while loop is way too complex.  if it takes more than 30 secs for an experienced programmer to figure out what's going on, that means you need to rewrite it
0
 
LVL 40

Expert Comment

by:Kyle Abrahams
ID: 8058785
>> but even experience C and C++ programmers are prone to make uncaught "silly errors" when using them

It's the programmer's fault then, not the language.  If the programmer doesn't make "silly errors", then the functions are quite useful.  Especially when you're trying to write efficient code.

> "C++ is absolutely reverse compatible, after all..."
I meant that you can use all C functions in c++, not the other way around.

> "if you check sources for your c++"

I was not debating how it was implemented.  I was just saying it could be done that way.
0
 

Author Comment

by:anxx0018
ID: 8058851
Do not worry about the program any more. I have figured out a good way to deal with it. But I have read your suggestions carefully and try to do good notes from them.



Do you guys know how to use stdin when you have inputs from multiple files?

Thank you very much!
0
 
LVL 46

Expert Comment

by:Kent Olsen
ID: 8058861

Back to your problem......  A lot of it is style.

Rewrite the Min() function as a macro:

#define Min(a,b) (a<b?a:b)

This will allow you to use it anywhere in the program with any data type or class that utilizes the '<' operator.  When written as a function, only int (or int compatible types) can be used and you may well want to compare long or float elsewhere in the program.


WordCmp() uses the 'new' operator needlessly.  It creates two new buffers each call and never 'delete's them.  The data that you want is already available to the function.  As an earlier post suggested, use C++ classes and functions.  If you really want to use a C style search, start the function like this:

int WordCmp(string k1, string k2)
{
 int len1,len2;

 char *s1 = k1.c_str();
 char *s2 = k2.c_str();
 
 while (*s1 || *s2)
 {
 /* perform comparisons
 }
 return /* strings are equal */
}



if (condition)
  return;
else
  ...

is wordy and lengthy.

if (condition)
  return;

is sufficient.


Lastly, I don't see a working sort algorithm in your code.  I'll leave it up to you to devise one.


Good Luck,
Kdo
0
 
LVL 7

Accepted Solution

by:
burcarpat earned 80 total points
ID: 8059056
ged325,

> "It's the programmer's fault then, not the language.  If the programmer doesn't make "silly errors", then the functions are quite useful.  Especially when you're trying to write efficient code."

of course, ged325.  but, if we follow that logic too keenly, we'll all need to code using assembler.  there is nothing wrong with assembler as far as the functionality goes.  if written correctly, it will always be faster and more memory efficient than anything you can come up with and all the bugs are actually always the programmer's fault.  yet, we don't use assembler and for a reason

function-wise, there is nothing you can't do in c, that you can in c++ ( that doesn't mean they are compatible, though ).  you can even fake class hierarchies and polymorphism, if you want to ( and, in fact, linux people use that kind of stuff all the time ).  sure, it'll be a lot more complex in c, than in c++ but it can be done.  yet, that's not the point.  the point is, this is c++, not c.  just because the legacy support is there, one should not automatically reach for it when other native alternatives exist

majority of the times you don't need the performance gain that *might* be provided by c-style strings anyway ( and, the only way to prove the opposite is to profile the actual code ).  in fact, std::string has certain advantages over char* such as reference-counting and thus for certain cases, it can actually be more optimum than using bare char*s.  another typical example is sorting using strings.  if you fall into the trap of thinking char* is always more efficient than std::string, and c-style functions are always faster than c++ counterparts, you might be surprised when you try to qsort() char*s using strcmp()

unless one understands the inner-workings of char*, std::string and other c-style functions very clearly, one should always choose std::string over char* and c++ functions over c-style functions

...

Kdo,

> "#define Min(a,b) (a<b?a:b)"

i think, that suggestion needs to be revised.   please see:

    http://www.gotw.ca/gotw/077.htm

the main problem is, something like "max(i+=2, j)" will blow up your macro big time and it's not uncommon to find such things in actual code.  because max looks like a function but in reality it is a macro, these things will happen ( and will cause long debugging sessions )

i think the general rule of "use c++, not c" also applies here.  it's generally best to avoid macros, which are a part of c ( c++ intended to remove macros altogether via template support but macros were too practically useful and used too widely for that )

a simple alternative might be:

    template <typename T>
    T
    min(const T& _a,
        const T& _b) {
      return (_a < _b) ? _a : _b;
    }; // min

an even better min/max definition is at

    http://www.cuj.com/experts/1904/alexandr.htm?topic=experts

...

anxx0018,
 
good luck w/ your code...
0
 

Author Comment

by:anxx0018
ID: 8059103
Thank you very much for your suggestions.


Do you guys know how to use stdin when you have inputs from multiple files?

Thank you very much!
0
 

Expert Comment

by:vinay_krishna
ID: 8063511
*line = buffer[];
0
 

Author Comment

by:anxx0018
ID: 8084553
burcarpat,

Thank you for your help! You are a very skilled programmer!

0

Featured Post

Enroll in August's Course of the Month

August's CompTIA IT Fundamentals course includes 19 hours of basic computer principle modules and prepares you for the certification exam. It's free for Premium Members, Team Accounts, and Qualified Experts!

Question has a verified solution.

If you are experiencing a similar issue, please ask a related question

What is C++ STL?: STL stands for Standard Template Library and is a part of standard C++ libraries. It contains many useful data structures (containers) and algorithms, which can spare you a lot of the time. Today we will look at the STL Vector. …
Container Orchestration platforms empower organizations to scale their apps at an exceptional rate. This is the reason numerous innovation-driven companies are moving apps to an appropriated datacenter wide platform that empowers them to scale at a …
Excel styles will make formatting consistent and let you apply and change formatting faster. In this tutorial, you'll learn how to use Excel's built-in styles, how to modify styles, and how to create your own. You'll also learn how to use your custo…
If you’ve ever visited a web page and noticed a cool font that you really liked the look of, but couldn’t figure out which font it was so that you could use it for your own work, then this video is for you! In this Micro Tutorial, you'll learn yo…
Suggested Courses

777 members asked questions and received personalized solutions in the past 7 days.

Join the community of 500,000 technology professionals and ask your questions.

Join & Ask a Question