7

Possible Duplicate:
Is there a strtol equivalent that does not require a null-terminated string?
strtod with limited string length

I am trying to convert c 'strings' into various c numeric types: int, float, long int... the 'strings' I have are not '\0' terminated chars, but I have lengths for every string, so I have to copy the chars into buffer, add '\0' to the end, then use atoi or strtol...

Are there some lib/functions that already implement functions like the following?

strToInt(char *str, int str_len)

strToFloat(char *str, int str_len)
Community
  • 1
  • 1
Mickey Shine
  • 12,187
  • 25
  • 96
  • 148
  • By definition, if the strings are *not* NUL-terminated, then they are *not* C-strings ;-) –  Mar 09 '12 at 09:01
  • 2
    Please don't close. The question is very different from the potential duplicate due to the added need for floating point (which has no easy "roll your own" solution). – R.. GitHub STOP HELPING ICE Mar 09 '12 at 10:05

4 Answers4

3

Maybe don't even bother with a library. In the integer case it'd be really easy to do it yourself:

int str2int(const char* str, int len)
{
    int i;
    int ret = 0;
    for(i = 0; i < len; ++i)
    {
        ret = ret * 10 + (str[i] - '0');
    }
    return ret;
}

For floats and doubles, you could use the same code for the integral part, and then a loop that decreases the influence of each successive character by a factor of ten for the decimal bit.

Extra work comes in with all the bells and whistles you want to add - negative numbers (I didn't bother with those in the example code, but they're easy enough to add), scientific notation, validity checking, etc. - but it's not that hard to do once you decide to sit down and do it.

Hope that helps!

Xavier Holt
  • 14,471
  • 4
  • 43
  • 56
  • Indeed... If any programmer find themselves having trouble to write utterly fundamental things like this in less than 10 minutes, I would strongly advise finding a good C programming book for beginners... – Lundin Mar 09 '12 at 09:21
  • 2
    Converting floating point numbers is **highly nontrivial**, and your algorithm is wrong. "Roll your own" for things like this is almost surely bad idea. Just `strndup` and `strtod` it. – R.. GitHub STOP HELPING ICE Mar 09 '12 at 09:39
2

C strings are by definition char buffers terminated by null. Otherwise those are not C strings.

I would say that the easiest way, if you have a buffer that is not a C string - convert it to string, and use the standard functions (atoi etc.). Usually it will not even require allocation of more memory, but only a copy of the current string.

MByD
  • 135,866
  • 28
  • 264
  • 277
2

Since in your usage case it seems like the non-null-terminated string exists as part of a larger string (non-numeric character immediately following the number), you can probably just use strtol and strtod as-is. They will automatically stop when they reach the end of the number, and in fact they'll give you a pointer to the next character if you ask them for it.

If the data in the buffer following the number is not further text, or if it might butt into a subsequent numeric character, ask yourself if you can be sure that the data is writable and not being read by any other thread while you're processing it. If so, just backup the following character and replace it with a null character, call strtol or strtod, then restore the character you overwrote.

If all else fails, use strndup (POSIX, or roll your own) to make a copy that's a C string. If you know the length is bounded, you could avoid allocation and just copy it into a local automatic array variable.

R.. GitHub STOP HELPING ICE
  • 208,859
  • 35
  • 376
  • 711
-1

You can use memcpy to copy the requires amount of bytes from source to the dest buffer, and append the \0 manually, which will make the byte sequence to a string, next pass it to atoi, strtol (and family). Why not simply null terminate the byte sequence instead of copying it to an intermediate buffer?

phoxis
  • 60,131
  • 14
  • 81
  • 117
  • the 'string' are just pointers pointing string presentation of numbers in a big c strings, so that they don't have '\0' at the end. obviously I can copy the chars into buffer, but it seems not so much have to do such intermediate step – Mickey Shine Mar 09 '12 at 09:01
  • The standard functions does not provide such interface, maybe you dynamically allocate exactly the amount of buffer needed, null terminate it, pass it to `strtol`, free the buffer? – phoxis Mar 09 '12 at 09:15
  • To the minimum, you could create a buffer on the stack so as to avoid an allocation! – Alexis Wilke Mar 22 '19 at 03:10