Help deleting leading zeros in a file

I have a list of numbers extracted and need to delete the leading zeros from them, but when i do so, the command I am using also deletes numbers that end in Zero as well. eg 10, 20, 30, etc

this is part of a larger script and the only way I can think of is to try and detect the 10,20 30 etc in the first part of a if statement then deal with the remainder but that i think is quite messy as there may be many of them

Ideas?

My input to check is like this file below and trying to process with this code snipopet

file="leadingzero.txt"     # input filename
while read line 
    do
        wardevent=${line##*[!1-9]}                     # remove leading Zero from the line
echo $wardevent
done <"$file"

File:

001
002
003
004
005
006
007
008
009
010
011
012
019
020
021

Thanks
Ken

Input file

 $ cat file
001
002
003
004
005
006
007
008
009
010
011
012
019
020
021

What is your expected output..?

this one?

 $ awk '{$1+=0}1' file
1
2
3
4
5
6
7
8
9
10
11
12
19
20
21

or this one....?

 awk '{sub(/^0/,"")}1' file
01
02
03
04
05
06
07
08
09
10
11
12
19
20
21

Always give your input and desired output.

Sorry for that and thanks
Yes i would like the output without the leading zeros as per this

$ awk '{$1+=0}1' file

Is there a way to do it using string processing rather than calling awk?
Reason being as the section of the file is only a selection from a much larger line that is processed as part of a much larger string. The rest of the code pulls out the numbers and then I need to stip the leading zeros before putting them in an array.

I only included the extracted part to avoid confusion with the rest of the code.

Ken

How large is the file overall, i.e. number of records?

You could shell script it like this:-

#!/bin/ksh

typeset -i col1                     # Define as integer

while read col1 rest
do
   echo "$col1 $rest"
done < input_file  > output_file

The run time may get long if the file is large though and you will get errors if any of the values in column1 are not numeric.

Does that work as a quick hit?

Perhaps you could do something with sed or awk to strip leading zeros if the file is bigger and the alapse time of the above code is not acceptable.

I hope that this helps

Robin
Liverpool/Blackburn
UK

also

while read line 
    do
        wardevent=$(expr $line + 0)                     # remove leading Zero from the line
echo $wardevent
done<file
1 Like

Dear pamu,
How does your code react with the following input? :-

0001
0002 123
0003 Hello

I regret that I get syntax errors for lines 2 & 3.

Robin

1 Like

Awesome thank you very much that is exactly what I need to achieve:b:

Thanks
Ken

As per the OP

He has already have code to separate the numbers here so, He just want to remove leading zeros.

In case you are interested in a much more efficient string processing approach which does not need to create an entirely new shell just to strip the zeroes, here's a modified version of pamu's suggestion:

while
    read line
do
    wardevent=${line#"${line%%[!0]*}"}
    echo $wardevent
done

That assumes (like pamu's suggestion) that the value of $line consists of nothing but digits. If that is not the case, then the read statement needs to be fortified and the echo statement should be abandoned in favor of printf and $wardevent double-quoted.

Regards,
Alister

while read v junk
do
    wardevent=$((10#$v))
    echo $wardevent
done < file
1 Like

Slight modification of pamu's code:

while read No REST; do   printf "%2d %s\n" "$No" "$REST"; done<file
 1 
 2 123
 3 Hello

Adapt printf's format string to your needs.

Like the shell built-in numerics, printf "%d" treats a value with a leading 0 as an octal value, so 08 and 09 give error.
A workaround is printf "%.f" .

3 Likes

... or give it the decimal prefix:

while read No REST; do   printf "%02d %s\n" $((10#$No)) "$REST"; done<file
01 
02 123
03 Hello
08 skl�fj
09 dfdsf

printf is a poor approach. Post #3 states that the result of stripping the leading zeroes will be saved for further use. To save printf's output, it's necessary to use command substitution, which does not improve upon the already accepted solution, $(expr ...) .

If the shell (or shells) which must run this code support the base# notation, I recommend MadeInGermany's arithmetic expansion approach, $((10#$v)) . It's efficient and so simple that it's immediately understandable.

If the code must run on a shell which does not support base# , then my suggestion is probably the best choice.

Regards,
Alister

1 Like

@alister, it would improve somewhat upon the accepted solution, since expr is an external command, whereas printf is not, although both would be slower than your suggested variable expansion of course.

Also $((10#$v)) is not available in every POSIX compliant shell like you stated

An advantage of the printf approach is that it would also handle cases like floating point and scientific notation and/or a leading plus signs..

1 Like

Thank you all for your solutions
Looks like my little problem created quite an interesting discussion :b:

Ken

:eek: Didn't I answer the question in post #4 in a way that others have replicated with more complex code? :eek:
I've written it as ksh, but the same works for bash :wink:

:confused: Not sure what all the worry is about. :confused:

For a faster process not reading line by line & looping, how about:-

sed s/^0*//g file

Does that fit the bill? It works for me. :cool:

I'd like to learn what I missed earlier and see if this is a better fit. :rolleyes:

Robin

You didn't read post #3, did you? :stuck_out_tongue:
:smiley:

So have I missed the point? :eek:
My reading of part of post #3:-

This suggested to me that there was more data on the line, not that the file was just a single column of numbers, which is why I gave a solution for a file like this:-

0001
0002 123
0003 Hello

Ho hum, I suppose that it will work for either. Do we have a happy questioner? That's the important bit I suppose. :rolleyes:

.... and hey, I've learnt a few techniques too, so I'm happy. :stuck_out_tongue:

Robin

Hi robin we do have a happy Questioner :slight_smile:
Lots of great ideas and solutions in here.

the reason I did not want to run either sed or awk is that the number in question is clipped out of a much longer line ( as a string). this has to repeated for many lines in the original files. Shelling out to awk / sed will make the loop processing to complicated where doing as part of a string is relatively easy within the loop.

Also this is a bash script but for the original question that was not important, but certainly interesting to read the differences in the responses.

Ken