LinuxQuestions.org
Review your favorite Linux distribution.
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 07-11-2019, 02:58 PM   #1
BW-userx
LQ Guru
 
Registered: Sep 2013
Location: Somewhere in my head.
Distribution: Slackware 14.2 current / ArcoLinux / Void Linux
Posts: 8,881

Rep: Reputation: 1854Reputation: 1854Reputation: 1854Reputation: 1854Reputation: 1854Reputation: 1854Reputation: 1854Reputation: 1854Reputation: 1854Reputation: 1854Reputation: 1854
Question replace only 1st occurrence of pattern using sed, or whatever works.


Looking this up and using the examples on every page. I am still getting an error.
Code:
sed: -e expression #1, char 3: unexpected `,'
when I remove the ',' comma I get a different error.
Code:
sed: -e expression #1, char 2: invalid usage of line address 0
Code:
$ 
sed --version
sed (GNU sed) 4.7
this is where I left off at, out of all of my tries.
Code:
 #!/bin/bash

runscript=$HOME/bin/wallhaven.sh
sp=29

changePrams()
{
      sed -n  '0|^STARTPAGE|s|(^S.*\)|STARTPAGE='$sp'|p'  "$runscript"
    
    if [[ $sp -gt '48'  ]] ; then
        sp=1
    else
        ((sp*2))
    fi
}
changePrams
bonus question:
a better way to write that check for value in BASH..

if x > y ? x = 0 : x*2

Last edited by BW-userx; 07-11-2019 at 03:02 PM.
 
Old 07-11-2019, 03:16 PM   #2
Turbocapitalist
Senior Member
 
Registered: Apr 2005
Distribution: Linux Mint, Devuan, OpenBSD
Posts: 4,022
Blog Entries: 3

Rep: Reputation: 1924Reputation: 1924Reputation: 1924Reputation: 1924Reputation: 1924Reputation: 1924Reputation: 1924Reputation: 1924Reputation: 1924Reputation: 1924Reputation: 1924
If you want it to run then use the q command to quit:

Code:
sed -n  "/^STARTPAGE/{s/^\(S.*\)/STARTPAGE=$sp/;ta;b;:a;p;q}"
Also the caret for start of the line must go first and then the parenthesis must be escaped if you are not using -r. Either way, the parentheses must match.
 
1 members found this post helpful.
Old 07-11-2019, 03:24 PM   #3
teckk
Senior Member
 
Registered: Oct 2004
Distribution: FreeBSD Arch
Posts: 2,167

Rep: Reputation: 437Reputation: 437Reputation: 437Reputation: 437Reputation: 437
Quote:
bonus question:
a better way to write that check for value in BASH..
Don't know if it's better.

Code:
x=46
xx=$((x > 48 ? 0 : x * 2))
echo "$xx"
96

x=54
xx=$((x > 48 ? 0 : x * 2))
echo "$xx"
0
 
1 members found this post helpful.
Old 07-11-2019, 03:36 PM   #4
BW-userx
LQ Guru
 
Registered: Sep 2013
Location: Somewhere in my head.
Distribution: Slackware 14.2 current / ArcoLinux / Void Linux
Posts: 8,881

Original Poster
Rep: Reputation: 1854Reputation: 1854Reputation: 1854Reputation: 1854Reputation: 1854Reputation: 1854Reputation: 1854Reputation: 1854Reputation: 1854Reputation: 1854Reputation: 1854
Quote:
Originally Posted by teckk View Post
Don't know if it's better.

Code:
x=46
xx=$((x > 48 ? 0 : x * 2))
echo "$xx"
96

x=54
xx=$((x > 48 ? 0 : x * 2))
echo "$xx"
0
that works, I was trying that and doing the assignment of value, ((x>23?x=0:x*2)) and that was my error.
Code:
 x=$((x > 24 ? 0 : x + 2)) ; echo $x
works

I decided to add 2 is all.

thanks!
 
Old 07-11-2019, 03:39 PM   #5
BW-userx
LQ Guru
 
Registered: Sep 2013
Location: Somewhere in my head.
Distribution: Slackware 14.2 current / ArcoLinux / Void Linux
Posts: 8,881

Original Poster
Rep: Reputation: 1854Reputation: 1854Reputation: 1854Reputation: 1854Reputation: 1854Reputation: 1854Reputation: 1854Reputation: 1854Reputation: 1854Reputation: 1854Reputation: 1854
Quote:
Originally Posted by Turbocapitalist View Post
If you want it to run then use the q command to quit:

Code:
sed -n  "/^STARTPAGE/{s/^\(S.*\)/STARTPAGE=$sp/;ta;b;:a;p;q}"
Also the caret for start of the line must go first and then the parenthesis must be escaped if you are not using -r. Either way, the parentheses must match.
what is all of this aftermath, ta;b;:a;p;q}, then q=quit, I've never seen anything like that before with sed. Shows you how much I use sed.

I got that caret thing from this page
https://www.theurbanpenguin.com/usin...t-first-match/
it shows a less detailed line to use.

ok, Looking at it again I do see what usage of {p:q}, but it is without the editing.

Last edited by BW-userx; 07-11-2019 at 03:44 PM.
 
Old 07-11-2019, 03:46 PM   #6
Turbocapitalist
Senior Member
 
Registered: Apr 2005
Distribution: Linux Mint, Devuan, OpenBSD
Posts: 4,022
Blog Entries: 3

Rep: Reputation: 1924Reputation: 1924Reputation: 1924Reputation: 1924Reputation: 1924Reputation: 1924Reputation: 1924Reputation: 1924Reputation: 1924Reputation: 1924Reputation: 1924
Quote:
Originally Posted by BW-userx View Post
what is all of this aftermath, I've never seen anything like that before with sed. Shows you how much I use sed.
It's more or less what it looks like you were trying to do with your first formula, the one that doesn't work.

Code:
sed -n  "
    /^STARTPAGE/ {
        s/^\(S.*\)/STARTPAGE=$sp/;
        ta;
        b;
        :a;
        p;
        q
    }"
The /pattern/{...} executes the {...} clause only if the pattern is found.

I'm not sure why you have the parenthesis, they are not used, but the s/// is a substitution.

The t means a conditional jump such that if the s/// did something then jump to the label. In this case the label is "a".

The b means an unconditional jump. Without a label, it jumps to the end of the script. In this case it is used to hop over the p for print.

The :a is the label :a, which is the destination of the aforementioned conditional jump.

The p prints.

The q quits the script, thus stopping after the first successful substitution.

I'm sure there are several ways to streamline that.
 
1 members found this post helpful.
Old 07-11-2019, 04:07 PM   #7
BW-userx
LQ Guru
 
Registered: Sep 2013
Location: Somewhere in my head.
Distribution: Slackware 14.2 current / ArcoLinux / Void Linux
Posts: 8,881

Original Poster
Rep: Reputation: 1854Reputation: 1854Reputation: 1854Reputation: 1854Reputation: 1854Reputation: 1854Reputation: 1854Reputation: 1854Reputation: 1854Reputation: 1854Reputation: 1854
for some reason sed was not liking the | pipe, and sed is suppose to allow the use of anything, it just needs to match, but not in this instance. strange, But it looks to be working now.
Code:
#!/bin/bash

runscript=$HOME/bin/wallhaven.sh
 x=1
 
changePrams()
{
    sed -i  '/^STARTPAGE/s/\(^S.*\)/STARTPAGE='$x'/' "$runscript"
    x=$((x>64?0:x+2))
}
#frist run
$runscript

	while sleep 1h
	do
	   changePrams
	   $runscript
	done
it's a start, I'll prob tweak it some more when I get way too many images.

Last edited by BW-userx; 07-11-2019 at 04:11 PM.
 
Old 07-11-2019, 04:10 PM   #8
BW-userx
LQ Guru
 
Registered: Sep 2013
Location: Somewhere in my head.
Distribution: Slackware 14.2 current / ArcoLinux / Void Linux
Posts: 8,881

Original Poster
Rep: Reputation: 1854Reputation: 1854Reputation: 1854Reputation: 1854Reputation: 1854Reputation: 1854Reputation: 1854Reputation: 1854Reputation: 1854Reputation: 1854Reputation: 1854
Quote:
Originally Posted by Turbocapitalist View Post
It's more or less what it looks like you were trying to do with your first formula, the one that doesn't work.

Code:
sed -n  "
    /^STARTPAGE/ {
        s/^\(S.*\)/STARTPAGE=$sp/;
        ta;
        b;
        :a;
        p;
        q
    }"
The /pattern/{...} executes the {...} clause only if the pattern is found.

I'm not sure why you have the parenthesis, they are not used, but the s/// is a substitution.

The t means a conditional jump such that if the s/// did something then jump to the label. In this case the label is "a".

The b means an unconditional jump. Without a label, it jumps to the end of the script. In this case it is used to hop over the p for print.

The :a is the label :a, which is the destination of the aforementioned conditional jump.

The p prints.

The q quits the script, thus stopping after the first successful substitution.

I'm sure there are several ways to streamline that.
well I am working with known factors. I know there is the word STARTPAGE in that script, only it is used more than once, so I only need to change the first one that sets its value to be used within that script. each time I run it that value will be increased until it hits a max value then reset it and start over.

post #7 shows how I am using this script.

Last edited by BW-userx; 07-11-2019 at 04:14 PM.
 
Old 07-11-2019, 06:19 PM   #9
syg00
LQ Veteran
 
Registered: Aug 2003
Location: Australia
Distribution: Lots ...
Posts: 17,923

Rep: Reputation: 2852Reputation: 2852Reputation: 2852Reputation: 2852Reputation: 2852Reputation: 2852Reputation: 2852Reputation: 2852Reputation: 2852Reputation: 2852Reputation: 2852
Quote:
Originally Posted by BW-userx View Post
for some reason sed was not liking the | pipe, and sed is suppose to allow the use of anything, it just needs to match, but not in this instance. strange, But it looks to be working now.
Nope - you can use (almost) anything as a separator, not for a specifying a RE - especially one used in an address range. Get that correct and you can certainly use the pipe in the substitution.
 
Old 07-11-2019, 06:30 PM   #10
BW-userx
LQ Guru
 
Registered: Sep 2013
Location: Somewhere in my head.
Distribution: Slackware 14.2 current / ArcoLinux / Void Linux
Posts: 8,881

Original Poster
Rep: Reputation: 1854Reputation: 1854Reputation: 1854Reputation: 1854Reputation: 1854Reputation: 1854Reputation: 1854Reputation: 1854Reputation: 1854Reputation: 1854Reputation: 1854
Quote:
Originally Posted by syg00 View Post
Nope - you can use (almost) anything as a separator, not for a specifying a RE - especially one used in an address range. Get that correct and you can certainly use the pipe in the substitution.
well I kind of figured that you could/should not repeated, or use a separator that would/could be in the text one is looking for. Id think that would confuse sed.


this was what I was using.
Code:
sed -i  '|^STARTPAGE|s|\(^S.*\)|STARTPAGE='$x'|' "$runscript"
to this
sed -i  '/^STARTPAGE/s/\(^S.*\)/STARTPAGE='$x'/' "$runscript"
and sed kept telling me unknown | something like that, but it was referencing the | pipe. and it stopped when I changed it to the / forward slash, or backslash depending on which end one is looking at.
 
Old 07-11-2019, 07:48 PM   #11
syg00
LQ Veteran
 
Registered: Aug 2003
Location: Australia
Distribution: Lots ...
Posts: 17,923

Rep: Reputation: 2852Reputation: 2852Reputation: 2852Reputation: 2852Reputation: 2852Reputation: 2852Reputation: 2852Reputation: 2852Reputation: 2852Reputation: 2852Reputation: 2852
Quote:
Originally Posted by BW-userx View Post
or use a separator that would/could be in the text one is looking for. Id think that would confuse sed.
That's usually the reason to use an alternate separator in the first place - say when parsing web addresses. Has always been the case.
 
Old 07-11-2019, 08:38 PM   #12
BW-userx
LQ Guru
 
Registered: Sep 2013
Location: Somewhere in my head.
Distribution: Slackware 14.2 current / ArcoLinux / Void Linux
Posts: 8,881

Original Poster
Rep: Reputation: 1854Reputation: 1854Reputation: 1854Reputation: 1854Reputation: 1854Reputation: 1854Reputation: 1854Reputation: 1854Reputation: 1854Reputation: 1854Reputation: 1854
I've always found the / being too confusing at first glance, when I first started looking at the how tos.

Code:
/\df/df/d\dfer\(.*)/\/
gobbley goobaly looking then read a little on sed and seen that one can use whatever for a separator and I picked the Pipe.
having to escape the http:\/\/'s
Code:
$ cat testhttp
http://www.gobble.com

$ sed 's/\/\//gooooo/' testhttp
http:gooooowww.gobble.com
I would not know real world http sedding, It has not been on my plate to have to do.
 
Old 07-11-2019, 09:14 PM   #13
MadeInGermany
Senior Member
 
Registered: Dec 2011
Location: Simplicity
Posts: 1,133

Rep: Reputation: 512Reputation: 512Reputation: 512Reputation: 512Reputation: 512Reputation: 512
The s command uses the following character as a delimiter.
The search-only /RE/ has the "syntactical" problem that the first / is used as the command.
But sed has defined the \cREc as an alternative:
So in your case you can do
Code:
sed -i '\|^STARTPAGE=| s|=.*|='$x'|' "$runscript"
In comparison, perl solved it more elegantly, by introducing an m command ("match"):
Code:
perl -pe -i  'm|^STARTPAGE=| and s|=.*|='$x'|' "$runscript"
 
1 members found this post helpful.
Old 07-11-2019, 11:02 PM   #14
Turbocapitalist
Senior Member
 
Registered: Apr 2005
Distribution: Linux Mint, Devuan, OpenBSD
Posts: 4,022
Blog Entries: 3

Rep: Reputation: 1924Reputation: 1924Reputation: 1924Reputation: 1924Reputation: 1924Reputation: 1924Reputation: 1924Reputation: 1924Reputation: 1924Reputation: 1924Reputation: 1924
Quote:
Originally Posted by MadeInGermany View Post
But sed has defined the \cREc as an alternative:
Nice, I had somehow a blind spot for that part of the manual page,

Code:
       \cregexpc
              Match lines matching the regular expression regexp.  The  c  may
              be any character.
so my proposed answer to BW-userx was less elegant. Speaking of less elegant, is there a simpler way to meet BW-userx's requirement about first match?


BW-userx, did you mean first match on any given line or first-match in the whole file?
 
Old 07-12-2019, 05:44 AM   #15
MadeInGermany
Senior Member
 
Registered: Dec 2011
Location: Simplicity
Posts: 1,133

Rep: Reputation: 512Reputation: 512Reputation: 512Reputation: 512Reputation: 512Reputation: 512
BW-userx' first attempt with a range works in the sense "first match in file".
Code:
sed -i '0,\|^STARTPAGE=| s|=.*|='$x'|' "$runscript"
 
  


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
sed: delete lines after last occurrence of a pattern in a file zugvogel Programming 4 11-17-2009 01:49 AM
grep till the 1st occurrence of a pattern raghu123 Programming 2 04-15-2009 05:47 AM
grep till the 1st occurrence of a pattern raghu123 Programming 1 04-15-2009 05:17 AM
SED replace string by occurrence uttam_h Programming 5 03-05-2008 10:02 PM
Replace every other occurrence of pattern Wynd Linux - General 8 12-14-2005 03:43 PM

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

All times are GMT -5. The time now is 04:18 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