From mboxrd@z Thu Jan 1 00:00:00 1970 Return-Path: Received: (qmail 2698 invoked from network); 28 Aug 2001 15:20:50 -0000 Received: from sunsite.dk (130.225.51.30) by ns1.primenet.com.au with SMTP; 28 Aug 2001 15:20:50 -0000 Received: (qmail 7851 invoked by alias); 28 Aug 2001 15:20:38 -0000 Mailing-List: contact zsh-workers-help@sunsite.dk; run by ezmlm Precedence: bulk X-No-Archive: yes X-Seq: 15718 Received: (qmail 7838 invoked from network); 28 Aug 2001 15:20:32 -0000 From: Bart Schaefer Message-Id: <1010828151649.ZM2643@candle.brasslantern.com> Date: Tue, 28 Aug 2001 15:16:49 +0000 In-Reply-To: <20010828061920.57606.qmail@web10406.mail.yahoo.com> Comments: In reply to Felix Rosencrantz "Re: Working with the historywords special parameter" (Aug 27, 11:19pm) References: <20010828061920.57606.qmail@web10406.mail.yahoo.com> X-Mailer: Z-Mail (5.0.0 30July97) To: Felix Rosencrantz , zsh-workers@sunsite.dk Subject: Re: Working with the historywords special parameter MIME-Version: 1.0 Content-Type: text/plain; charset=us-ascii On Aug 27, 11:19pm, Felix Rosencrantz wrote: } } --- Bart Schaefer wrote: } >Have you tried using $history instead of $historywords? You want the } >word that comes immediately after $words[CURRENT-1] in every history } >line that contains $word[CURRENT-1], right? } > } > local w p h r } > w=${(q)words[CURRENT-1]} } > p=$'\0'$w$'\0' } > h=$'\0'${(pj:\0:)${(z)history[(R)*$w*]}} } > r=( ${${(ps:\1:)h//$~p/$'\1'}%%$'\0'*} ) } > compadd -a r } > } >This assumes there are no literal NUL or ctrl-A characters in the } >history, but that seems a pretty safe assumption. } } The other problem is that it didn't know about line boundaries. So if } the searched for word was at the end of the line, then it would return } a match for the previous command, which is wrong. Stick a $'\1' on the end of each line so that $'\0'$w$'\0' won't match the last word: local w p h r w=${(q)words[CURRENT-1]} p=$'\0'$w$'\0' # h=( ${^history[(R)*$w*]}$'\1' ) h=$'\0'${(pj:\0:)${(z)h}} r=( ${${(ps:\1:)h//$~p/$'\1'}%%$'\0'*} ) # compadd -a r To see which is faster, you can replace the three lines between the `#' with: r=() for h in $history[(R)*$w*] do h=$'\0'${(pj:\0:)${(z)h}} r[$#r+1]=( ${${(ps:\1:)h//$~p/$'\1'}%%$'\0'*} ) done I suspect the first way is faster because it does fewer, though larger, memory allocations. The loop body could be one line if not for the need to prepend $'\0' to the join. } Also, I was wondering if the (z) modifier applied to the elements of } history would always return the same results as found by historywords? No, it won't. $historywords is more like $=history, but it isn't quite that either -- the rules for what is a "word" in $historywords are a bit odd. E.g., quoted strings are broken up at whitespace, but =(...) are kept as single words. Also, it appears that $historywords has the words from the current input line, whereas $history doesn't get that line added until after the command has been parsed -- but I'm not sure about that. I think ${(z)history} is more accurate for purposes of completion. -- Bart Schaefer Brass Lantern Enterprises http://www.well.com/user/barts http://www.brasslantern.com Zsh: http://www.zsh.org | PHPerl Project: http://phperl.sourceforge.net