AWK/SED: handle max chars in a line

Hi all,

I hope you guys can help me.
I prefer SED/AWK solutions if possible. For my shame it didn't work for me :o
ISSUE: :wall:

1\3

1/$4\@7\
1234567890123456789\
1234567890123456789,\
1234567890123456789\
123456789012
12345
1234567890123456789\
1234567890123456789,\
1234

Information:
If a line has more than 19 chars, it uses a "\" as 20th char and proceeds in next line.
This is present as you see.

Task:
I changed lines, therefore they do no longer fit into the 20 chars.
E.g. i add a ",". I want to put it into the next line and correct here the 20 chars rule and this for all following lines. Until it's no longer needed.

Solution::smiley:

1\3

1/$4\@7\
1234567890123456789\
1234567890123456789\
,123456789012345678\
9123456789012
12345
1234567890123456789\
1234567890123456789\
,1234

Thanks a lot!!! :wink:
_______________________
Tried things in style of:
One solution: Use two vars saving the lines... removing additional , saving this string and writing it in front of the next line holding var. Than use again previous var and read this. Until line has <19 char.
Shouldn't be that hard... but i'm not familiar with the syntax :confused:
______
length > 20...
awk '/.../ use_vars=$0; if(line){print line ORS $0; line=""}}' file

See if this works for you:

#!/usr/bin/ksh
typeset -i mLen
mPrevLine=''
sed 's/\\//' Inp_File | while read mLine
do
  mLine2=${mPrevLine}${mLine}
  mLen=${#mLine2}
  if [[ ${mLen} -ge 20 ]]; then
    while [[ ${mLen} -ge 20 ]]; do
      mOutLine=$(echo ${mLine2} | cut -c1-19)
      echo ${mOutLine}'\'
      mLine2=$(echo ${mLine2} | cut -c20-)
      mLen=${#mLine2}
      mPrevLine=${mLine2}
    done
  else
    echo ${mLine2}
    mPrevLine=''
  fi
done

PS: According to your rule, your solution should not have a "\" on the following line:

...
1234567890123456789\ <=====
1234567890123456789\
1234
1 Like

Thanks a lot I will try.
Maybe you missunderstood me, I'm sorry if i explained to bad.
The ISSUE code was previousely done with this rule. It means whereever a "\" is, is NO newline. So its a line break character.
e.G. for linebreak after 5 chars:

wordAwordBwordC

is changed automatically to:

wordA\
wordB\
wordC

I added now a string to wordB:

wordA\
wordB_ADD\
wordC

should now result in following (I can't run the automatic tool again):

wordA\
wordB\
_ADDw\
ordC

So i'll check this and let u know if it worked... thanks so far!

cat input.txt | awk '{
if (length($0)+length(APPEND) < 20 ){
 TMP = APPEND $0
 gsub(/\\/,"",TMP)
 print TMP
 APPEND=""
}else{
 
 TMP = APPEND $0 
 gsub(/\\/,"",TMP)
 LINE = substr(TMP,1,19)
 APPEND = substr(TMP,20)
 print LINE "\\"

}
 
}'

try this

1 Like

@Shell life
EDIT: Solution nearly works. Thanks a lot. Just the first "\" is wrongly removed. If 19 char + "\" than do nothing. Means it was a longer char which was splitted prev. correctly. And do not remove "\" within lines.

NewTestcode:
Just remove "\" if it's last char in line and if line has >20 chars.
Remember the next line holds also the additional chars which were cut regarding to this rule!

AB!"�$&\\/()=?@\.*'A
12345678901234567890
1234567890123456789\
1234567890123456789,\
1234567890123456789\
123456789012
1234567890123456789\
1234567890123456789,\
A\B/C@D

newline_possible\/()

Result should be:

AB!"�$&\\/()=?@\.*'A
12345678901234567890
1234567890123456789\
1234567890123456789\
,123456789012345678\
9123456789012
1234567890123456789\
1234567890123456789\
,A\B/C@D

newline_possible\/()

If line is like:
12345678901234567890
and no "\" at the end -> do nothing.

Only if the last char of the 20 is a "\" than it's a splittet line. If there are 20 chars w/o a "\" nothing should be changed.
So 20 chars with "\" at the end means it was previously smth. bigger which was splitted.

So the "\" should just be removed if the line.length > 20 & the last char is a "\".
Tried to remove or move the sed command but i dont know how to let the loop run w/o sed :wink:

@UVI
Unfortunately it says syntax error... couldn't find the reson... could u recheck this please?

Thanks a lot!

---------- Post updated 20th Apr 2011 at 10:00 AM ---------- Previous update was 19th Apr 2011 at 07:03 PM ----------

Hmmm i don't get it...
additional check like: ${mline2: -1} -eq '\'
or with tail command

so much options... but my syntax is wrong :-/
Help is needed - thanks

Please, first verify if you do not have in your input file the octal 251 which is �.

If you do, then choose another special character that is not in your file.

#!/usr/bin/ksh
typeset -i mLen
mPrevLine=''
tr '\\' '\251' < Inp_File | while read mLine
do
  mLine2=${mPrevLine}${mLine}
  mLen=${#mLine2}
  if [[ ${mLen} -gt 20 ]]; then
    mLine2=$(echo ${mLine2} | sed 's/.$//')
    while [[ ${mLen} -gt 20 ]]; do
      mOutLine=$(echo ${mLine2} | cut -c1-19)
      echo ${mOutLine}'\'
      mLine2=$(echo ${mLine2} | cut -c20-)
      mLen=${#mLine2}
      mPrevLine=${mLine2}
    done
  else
    echo ${mLine2}
    mPrevLine=''
  fi
done | tr '\251' '\\'
1 Like