LinuxQuestions.org
Share your knowledge at the LQ Wiki.
Go Back   LinuxQuestions.org > Forums > Non-*NIX Forums > Programming
User Name
Password
Programming This forum is for all programming questions.
The question does not have to be directly related to Linux and any language is fair game.

Notices


Reply
  Search this Thread
Old 08-23-2008, 08:51 AM   #1
dina3e
Member
 
Registered: Mar 2008
Location: Bangalore
Distribution: Enterprise Red Hat linux
Posts: 98

Rep: Reputation: 16
operation of "tac" in sed


i had gone through "sed" i found that the "tac" implemntion in sed. it really work fine.

sed '1!G;h;$!d' file_name

but my question is how the internally the 'sed' works for this line of code
how the h(hold) and G(get) works in the hold space to pattern space in the execution of the hole file .
 
Old 08-24-2008, 11:54 AM   #2
ta0kira
Senior Member
 
Registered: Sep 2004
Distribution: FreeBSD 9.1, Kubuntu 12.10
Posts: 3,078

Rep: Reputation: Disabled
I have an idea of how it works, but I'm having trouble making it into something logical. Try the following and look at the differences in their outputs:
Code:
ls -ld ~ | sed 'G;h'
ls -ld ~ | sed '1!G;h'
ls -l ~ | sed 'G;h'
ls -l ~ | sed '1!G;h'
ls -l ~ | sed '1!G;h;$!d'
I'm not sure how that extra blank line ends up in the hold space. I'm probably missing something.
ta0kira
 
Old 08-24-2008, 01:36 PM   #3
Kenhelm
Member
 
Registered: Mar 2008
Location: N. W. England
Distribution: Mandriva
Posts: 341

Rep: Reputation: 143Reputation: 143
sed '1!G;h;$!d' does this to each line in turn:-
If it's not line1, append '\nHold space contents' to it (\n = newline);
Then copy it to the hold space (deletes previous contents);
Then, if it's not the last line, delete it.

The whole file ends up on the last line, other lines having been deleted.
e.g. A file with 3 lines A, B, C
Code:
                  State after each line has been processed by sed
Lines processed           0         1         2         3
Contents of line1         A         Line1 has been deleted
Contents of line2         B         B         Line2 has been deleted
Contents of line3         C         C         C         C\nB\nA

Contents of hold space    Empty     A         B\nA      C\nB\nA
 
Old 08-24-2008, 05:34 PM   #4
Mr. C.
Senior Member
 
Registered: Jun 2008
Posts: 2,529

Rep: Reputation: 62
Sometimes its simplifies understanding by translate sed code into more natural pseudocode:
Code:
sed '1!G;h;$!d'

#1
if not line 1 then
  append newline + hold space to end of pattern space
endif

#2
move pattern space to hold space

#3
if not last line then
  delete pattern space
endif
Keep in mind the line number of the pattern space doesn't have to change with each change to pattern or hold space. Rather, line numbers are considered as *input* lines, not pattern space lines numbers.

Last edited by Mr. C.; 08-24-2008 at 06:30 PM.
 
Old 08-24-2008, 06:08 PM   #5
ta0kira
Senior Member
 
Registered: Sep 2004
Distribution: FreeBSD 9.1, Kubuntu 12.10
Posts: 3,078

Rep: Reputation: Disabled
I think it's pretty obvious what the commands mean, but I don't think anyone's explained how that results in reversing of the lines. I've gotten as far as the pseudo-code in my head, but it doesn't seem to translate into the end result. I've been executing it one line at a time in my head and honestly can't explain the state of each buffer at every step of the way, which is what I think OP is asking.
ta0kira
 
Old 08-24-2008, 06:40 PM   #6
Mr. C.
Senior Member
 
Registered: Jun 2008
Posts: 2,529

Rep: Reputation: 62
Kenhelm's diagram shows the state of each line. I've edited my post above to label Steps as #1, #2, and #3. From these descriptions, it is pretty trivial to construct the flow:

For file containing:
A
B
C


First, for line 1. Pattern space for line 1 is A. Step #1 is skipped, because we're on line 1. Step #2 moves pattern space (A) to hold space which is empty. Hold space is now A. Step #3 deletes pattern space, so Pattern space for line 1 is now empty. Result: Hold space = "A", Pattern space = "".

Now, for line 2. Pattern space is "B" (because line 2 was just read). Step #1 appends newline + hold space to pattern space, thus "\n" + "A" goes to end of current pattern space of "B". Leaves pattern space as "B\nA". Step #2 moves pattern space of "B\n\A" to hold space. Step #3 deletes pattern space. Result: Hold space = "B\nA", Pattern space = "".

Finally, for line 3. Pattern space is "C" (again, this was just read). Step #1 appends newline + hold space to pattern space, thus "\n" + "B\nA" goes to end of current pattern space of "C". Leaves pattern space as "C\nB\nA". Step #2 copies pattern space to hold space. Hold space now "C\nB\nA". Step #3 is skipped, because we're at last line. Result: Hold space = "C\nB\nA", Pattern space = "C\nB\nA".

Sed's default action is to print pattern space, which is "C\nB\nA", the reverse of the input. So output is:

C
B
A

QED
 
Old 08-24-2008, 07:28 PM   #7
Kenhelm
Member
 
Registered: Mar 2008
Location: N. W. England
Distribution: Mandriva
Posts: 341

Rep: Reputation: 143Reputation: 143
Another diagram:
Again using a file of 3 lines A, B, C
Code:
                       Pattern space               Hold space
1st cycle:
after line1 input           A                         Empty
after 1!G                   A                         Empty
after h                     A                         A
after $!d                   Empty                     A

2nd cycle:
after line2 input           B                         A
after 1!G                   B\nA                      A
after h                     B\nA                      B\nA
after $!d                   Empty                     B\nA

3rd cycle:
after line3 input           C                         B\nA
after 1!G                   C\nB\nA                   B\nA
after h                     C\nB\nA                   C\nB\nA
after $!d                   C\nB\nA                   C\nB\nA
 
Old 08-24-2008, 08:45 PM   #8
ta0kira
Senior Member
 
Registered: Sep 2004
Distribution: FreeBSD 9.1, Kubuntu 12.10
Posts: 3,078

Rep: Reputation: Disabled
Thanks. Very helpful.
ta0kira
 
  


Reply


Thread Tools Search this Thread
Search this Thread:

Advanced Search

Posting Rules
You may not post new threads
You may not post replies
You may not post attachments
You may not edit your posts

BB code is On
Smilies are On
[IMG] code is Off
HTML code is Off



Similar Threads
Thread Thread Starter Forum Replies Last Post
"creating symbolic link" "operation not permitted" wheni Linux - Newbie 3 05-08-2011 01:36 AM
Logged in as "root"/Fedora 8 but get "Operation not permitted" when using "chmod etc gosunlee Linux - Newbie 7 02-10-2008 05:56 AM
kdenlive: on export, there's a tac tac tac in the sound output eantoranz Linux - Software 5 10-20-2007 11:20 AM
Replacing "function(x)" with "x" using sed/awk/smth Griffon26 Linux - General 3 11-22-2006 10:47 AM
searching "TIC TAC TOE" bash script LV-chronos Linux - Newbie 5 05-29-2005 02:20 PM

LinuxQuestions.org > Forums > Non-*NIX Forums > Programming

All times are GMT -5. The time now is 02:02 AM.

Main Menu
Advertisement
My LQ
Write for LQ
LinuxQuestions.org is looking for people interested in writing Editorials, Articles, Reviews, and more. If you'd like to contribute content, let us know.
Main Menu
Syndicate
RSS1  Latest Threads
RSS1  LQ News
Twitter: @linuxquestions
Facebook: linuxquestions Google+: linuxquestions
Open Source Consulting | Domain Registration