From mboxrd@z Thu Jan 1 00:00:00 1970 Path: news.gmane.io!.POSTED.blaine.gmane.org!not-for-mail From: =?utf-8?Q?Mattias_Engdeg=C3=A5rd?= Newsgroups: gmane.emacs.devel Subject: Re: master 87e422f: Beef up the Emacs string utility set a bit Date: Tue, 22 Dec 2020 11:41:01 +0100 Message-ID: <84D3EA2C-C81C-4056-AE71-0458905F231D@acm.org> References: <20201221175345.27592.89597@vcs0.savannah.gnu.org> <20201221175347.9F1B820B76@vcs0.savannah.gnu.org> <87eejjdn8e.fsf@gnus.org> <87a6u7dmnw.fsf@gnus.org> Mime-Version: 1.0 (Mac OS X Mail 12.4 \(3445.104.17\)) Content-Type: multipart/mixed; boundary="Apple-Mail=_0B559A6D-71A9-42FE-9F5A-8A4568B01810" Injection-Info: ciao.gmane.io; posting-host="blaine.gmane.org:116.202.254.214"; logging-data="28743"; mail-complaints-to="usenet@ciao.gmane.io" Cc: Stefan Kangas , emacs-devel@gnu.org To: Lars Ingebrigtsen Original-X-From: emacs-devel-bounces+ged-emacs-devel=m.gmane-mx.org@gnu.org Tue Dec 22 11:42:24 2020 Return-path: Envelope-to: ged-emacs-devel@m.gmane-mx.org Original-Received: from lists.gnu.org ([209.51.188.17]) by ciao.gmane.io with esmtps (TLS1.2:ECDHE_RSA_AES_256_GCM_SHA384:256) (Exim 4.92) (envelope-from ) id 1krf7Y-0007NV-4u for ged-emacs-devel@m.gmane-mx.org; Tue, 22 Dec 2020 11:42:24 +0100 Original-Received: from localhost ([::1]:48830 helo=lists1p.gnu.org) by lists.gnu.org with esmtp (Exim 4.90_1) (envelope-from ) id 1krf7X-0003wN-7U for ged-emacs-devel@m.gmane-mx.org; Tue, 22 Dec 2020 05:42:23 -0500 Original-Received: from eggs.gnu.org ([2001:470:142:3::10]:37562) by lists.gnu.org with esmtps (TLS1.2:ECDHE_RSA_AES_256_GCM_SHA384:256) (Exim 4.90_1) (envelope-from ) id 1krf6W-00037Z-Hx for emacs-devel@gnu.org; Tue, 22 Dec 2020 05:41:21 -0500 Original-Received: from mail1444c50.megamailservers.eu ([91.136.14.44]:38452 helo=mail264c50.megamailservers.eu) by eggs.gnu.org with esmtps (TLS1.2:ECDHE_RSA_AES_256_GCM_SHA384:256) (Exim 4.90_1) (envelope-from ) id 1krf6U-0005V2-8V for emacs-devel@gnu.org; Tue, 22 Dec 2020 05:41:20 -0500 X-Authenticated-User: mattiase@bredband.net DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/simple; d=megamailservers.eu; s=maildub; t=1608633664; bh=7+0qvj+HHY91LywjWTXxTP+Wt1mTMPmOM/70JfhlXHA=; h=From:Subject:Date:In-Reply-To:Cc:To:References:From; b=DiDOmk/Utlrxeh2djeaoskWSIBC56VmSeEHiJy72VP+VbZeNwBnvp56Hts9ggKbMM CPG7NRAo8cnm9su0nqJ/Ltfgcc/rRo99SD56XGbMyc4NB6W5h4IFGjuKpG7Irdrnmc yObZRsOxNiRDeNyClvw6J9SO+rsCO5M9geVGHihA= Feedback-ID: mattiase@acm.or Original-Received: from stanniol.lan (c-064ae655.032-75-73746f71.bbcust.telenor.se [85.230.74.6]) (authenticated bits=0) by mail264c50.megamailservers.eu (8.14.9/8.13.1) with ESMTP id 0BMAf14V026892; Tue, 22 Dec 2020 10:41:03 +0000 In-Reply-To: <87a6u7dmnw.fsf@gnus.org> X-Mailer: Apple Mail (2.3445.104.17) X-CTCH-RefID: str=0001.0A782F1F.5FE1CD40.001C, ss=1, re=0.000, recu=0.000, reip=0.000, cl=1, cld=1, fgs=0 X-CTCH-VOD: Unknown X-CTCH-Spam: Unknown X-CTCH-Score: 0.000 X-CTCH-Flags: 0 X-CTCH-ScoreCust: 0.000 X-CSC: 0 X-CHA: v=2.3 cv=bPlo382Z c=1 sm=1 tr=0 a=Ni+dBsiEfW2GqKMPYZim9A==:117 a=Ni+dBsiEfW2GqKMPYZim9A==:17 a=M51BFTxLslgA:10 a=14ohH5GubWcNLWQIe3cA:9 a=CjuIK1q_8ugA:10 a=G57gj_DQiDx_LzVD3k4A:9 a=B2y7HmGcmWMA:10 X-Origin-Country: SE Received-SPF: softfail client-ip=91.136.14.44; envelope-from=mattiase@acm.org; helo=mail264c50.megamailservers.eu X-Spam_score_int: -11 X-Spam_score: -1.2 X-Spam_bar: - X-Spam_report: (-1.2 / 5.0 requ) BAYES_00=-1.9, DKIM_SIGNED=0.1, DKIM_VALID=-0.1, SPF_HELO_NONE=0.001, SPF_SOFTFAIL=0.665 autolearn=no autolearn_force=no X-Spam_action: no action X-BeenThere: emacs-devel@gnu.org X-Mailman-Version: 2.1.23 Precedence: list List-Id: "Emacs development discussions." List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Errors-To: emacs-devel-bounces+ged-emacs-devel=m.gmane-mx.org@gnu.org Original-Sender: "Emacs-devel" Xref: news.gmane.io gmane.emacs.devel:261473 Archived-At: --Apple-Mail=_0B559A6D-71A9-42FE-9F5A-8A4568B01810 Content-Transfer-Encoding: quoted-printable Content-Type: text/plain; charset=us-ascii Thanks for the good work! I suggest that 'string-limit' be replaced with = two separate functions, 'string-prefix' and 'string-suffix', because = these are two different operations and it makes no sense to multiplex = them onto a single function with an argument saying which one we are = going to use. Suggested patch attached. The names can be discussed; for example, = 'string-left' and 'string-right' would do just as well. If someone prefers saturating semantics for negative length arguments, = then that's an option too. Ie, in case we want (string-prefix "abc" -2) to yield the empty string instead of an error. I think an error is more = useful. The new functions are now inline (defsubst) in keeping with the spirit = of subr-x.el. (We really should inline these better!) --Apple-Mail=_0B559A6D-71A9-42FE-9F5A-8A4568B01810 Content-Disposition: attachment; filename=0001-Replace-string-limit-with-string-prefix-and-string-s.patch Content-Type: application/octet-stream; x-unix-mode=0644; name="0001-Replace-string-limit-with-string-prefix-and-string-s.patch" Content-Transfer-Encoding: quoted-printable =46rom=20799aa76f2aa2fbbb2d1264a9bfdb6208edfbff65=20Mon=20Sep=2017=20= 00:00:00=202001=0AFrom:=20=3D?UTF-8?q?Mattias=3D20Engdeg=3DC3=3DA5rd?=3D=20= =0ADate:=20Tue,=2022=20Dec=202020=2011:23:39=20+0100=0A= Subject:=20[PATCH]=20Replace=20string-limit=20with=20string-prefix=20and=20= string-suffix=0A=0AHave=20separate=20functions=20for=20distinct=20= operations=20instead=20of=0Amultiplexing=20them=20both=20onto=20a=20= single=20function.=0A=0A*=20doc/lispref/strings.texi=20(Creating=20= Strings):=0A*=20etc/NEWS=20(https):=0A*=20lisp/emacs-lisp/shortdoc.el=20= (string):=0AUpdate=20documentation=20and=20announcement.=0A*=20= lisp/emacs-lisp/subr-x.el=20(string-limit):=20Remove.=0A(string-prefix,=20= string-suffix):=20New.=0A*=20test/lisp/emacs-lisp/subr-x-tests.el=20= (subr-string-limit):=20Remove.=0A(subr-string-prefix,=20= subr-string-suffix):=20New=20tests.=0A---=0A=20doc/lispref/strings.texi=20= =20=20=20=20=20=20=20=20=20=20=20=20|=2012=20++++++++----=0A=20etc/NEWS=20= =20=20=20=20=20=20=20=20=20=20=20=20=20=20=20=20=20=20=20=20=20=20=20=20=20= =20=20=20|=20=202=20+-=0A=20lisp/emacs-lisp/shortdoc.el=20=20=20=20=20=20= =20=20=20=20|=2010=20++++++----=0A=20lisp/emacs-lisp/subr-x.el=20=20=20=20= =20=20=20=20=20=20=20=20|=2029=20++++++++++++++++------------=0A=20= test/lisp/emacs-lisp/subr-x-tests.el=20|=2022=20++++++++++++++-------=0A=20= 5=20files=20changed,=2047=20insertions(+),=2028=20deletions(-)=0A=0Adiff=20= --git=20a/doc/lispref/strings.texi=20b/doc/lispref/strings.texi=0Aindex=20= ef848ac510..b71279d5d6=20100644=0A---=20a/doc/lispref/strings.texi=0A+++=20= b/doc/lispref/strings.texi=0A@@=20-405,12=20+405,16=20@@=20Creating=20= Strings=0A=20will=20not=20be=20shortened.=0A=20@end=20defun=0A=20=0A= -@defun=20string-limit=20string=20length=20&optional=20end=0A+@defun=20= string-prefix=20string=20length=0A=20If=20@var{string}=20is=20shorter=20= than=20@var{length},=20@var{string}=20is=20returned=0A=20as=20is.=20=20= Otherwise,=20return=20a=20substring=20of=20@var{string}=20consisting=20= of=0A-the=20first=20@var{length}=20characters.=20=20If=20the=20optional=20= @var{end}=0A-parameter=20is=20given,=20return=20a=20string=20of=20the=20= @var{length}=20last=0A-characters=20instead.=0A+the=20first=20= @var{length}=20characters.=0A+@end=20defun=0A+=0A+@defun=20string-suffix=20= string=20length=0A+If=20@var{string}=20is=20shorter=20than=20= @var{length},=20@var{string}=20is=20returned=0A+as=20is.=20=20Otherwise,=20= return=20a=20substring=20of=20@var{string}=20consisting=20of=0A+the=20= last=20@var{length}=20characters.=0A=20@end=20defun=0A=20=0A=20@defun=20= string-lines=20string=20&optional=20omit-nulls=0Adiff=20--git=20= a/etc/NEWS=20b/etc/NEWS=0Aindex=2046b8435a14..6ad95f7ca4=20100644=0A---=20= a/etc/NEWS=0A+++=20b/etc/NEWS=0A@@=20-1442,7=20+1442,7=20@@=20that=20= makes=20it=20a=20valid=20button.=0A=20=0A=20+++=0A=20***=20A=20number=20= of=20new=20string=20manipulation=20functions=20have=20been=20added.=0A= -'string-clean-whitespace',=20'string-fill',=20'string-limit',=0A= +'string-clean-whitespace',=20'string-fill',=20'string-prefix',=20= 'string-suffx',=0A=20'string-lines',=20'string-pad',=20= 'string-chop-newline'=20and=20'string-slice'.=0A=20=0A=20+++=0Adiff=20= --git=20a/lisp/emacs-lisp/shortdoc.el=20b/lisp/emacs-lisp/shortdoc.el=0A= index=20e9e1be1d55..0603046bf6=20100644=0A---=20= a/lisp/emacs-lisp/shortdoc.el=0A+++=20b/lisp/emacs-lisp/shortdoc.el=0A@@=20= -143,10=20+143,12=20@@=20string=0A=20=20=20(substring=0A=20=20=20=20= :eval=20(substring=20"foobar"=200=203)=0A=20=20=20=20:eval=20(substring=20= "foobar"=203))=0A-=20=20(string-limit=0A-=20=20=20:eval=20(string-limit=20= "foobar"=203)=0A-=20=20=20:eval=20(string-limit=20"foobar"=203=20t)=0A-=20= =20=20:eval=20(string-limit=20"foobar"=2010))=0A+=20=20(string-prefix=0A= +=20=20=20:eval=20(string-prefix=20"abcde"=203)=0A+=20=20=20:eval=20= (string-prefix=20"abcde"=2010))=0A+=20=20(string-suffix=0A+=20=20=20= :eval=20(string-suffix=20"abcde"=203)=0A+=20=20=20:eval=20(string-suffix=20= "abcde"=2010))=0A=20=20=20(split-string=0A=20=20=20=20:eval=20= (split-string=20"foo=20bar")=0A=20=20=20=20:eval=20(split-string=20= "|foo|bar|"=20"|")=0Adiff=20--git=20a/lisp/emacs-lisp/subr-x.el=20= b/lisp/emacs-lisp/subr-x.el=0Aindex=2009c4649817..b775989a88=20100644=0A= ---=20a/lisp/emacs-lisp/subr-x.el=0A+++=20b/lisp/emacs-lisp/subr-x.el=0A= @@=20-286,20=20+286,25=20@@=20string-fill=0A=20=20=20=20=20=20=20= (fill-region=20(point-min)=20(point-max)))=0A=20=20=20=20=20= (buffer-string)))=0A=20=0A-(defun=20string-limit=20(string=20length=20= &optional=20end)=0A-=20=20"Return=20(up=20to)=20a=20LENGTH=20substring=20= of=20STRING.=0A-If=20STRING=20is=20shorter=20than=20or=20equal=20to=20= LENGTH,=20the=20entire=20string=0A-is=20returned=20unchanged.=0A-=0A-If=20= STRING=20is=20longer=20than=20LENGTH,=20return=20a=20substring=20= consisting=20of=0A-the=20first=20LENGTH=20characters=20of=20STRING.=20=20= If=20END=20is=20non-nil,=20return=0A-the=20last=20LENGTH=20characters=20= instead."=0A+(defsubst=20string-prefix=20(string=20length)=0A+=20=20= "Return=20the=20first=20LENGTH=20characters=20of=20STRING.=0A+If=20= LENGTH=20is=20greater=20than=20the=20length=20of=20STRING,=20return=20= STRING."=0A+=20=20(declare=20(side-effect-free=20t)=20(pure=20t))=0A=20=20= =20(unless=20(natnump=20length)=0A=20=20=20=20=20(signal=20= 'wrong-type-argument=20(list=20'natnump=20length)))=0A-=20=20(cond=0A-=20= =20=20((<=3D=20(length=20string)=20length)=20string)=0A-=20=20=20(end=20= (substring=20string=20(-=20(length=20string)=20length)))=0A-=20=20=20(t=20= (substring=20string=200=20length))))=0A+=20=20(if=20(<=20length=20= (length=20string))=0A+=20=20=20=20=20=20(substring=20string=200=20= length)=0A+=20=20=20=20string))=0A+=0A+(defsubst=20string-suffix=20= (string=20length)=0A+=20=20"Return=20the=20last=20LENGTH=20characters=20= of=20STRING.=0A+If=20LENGTH=20is=20greater=20than=20the=20length=20of=20= STRING,=20return=20STRING."=0A+=20=20(declare=20(side-effect-free=20t)=20= (pure=20t))=0A+=20=20(unless=20(natnump=20length)=0A+=20=20=20=20(signal=20= 'wrong-type-argument=20(list=20'natnump=20length)))=0A+=20=20(if=20(<=20= length=20(length=20string))=0A+=20=20=20=20=20=20=20=20(substring=20= string=20(-=20(length=20string)=20length))=0A+=20=20=20=20=20=20string))=0A= =20=0A=20(defun=20string-lines=20(string=20&optional=20omit-nulls)=0A=20=20= =20"Split=20STRING=20into=20a=20list=20of=20lines.=0Adiff=20--git=20= a/test/lisp/emacs-lisp/subr-x-tests.el=20= b/test/lisp/emacs-lisp/subr-x-tests.el=0Aindex=20854d61ed28..88b763fa40=20= 100644=0A---=20a/test/lisp/emacs-lisp/subr-x-tests.el=0A+++=20= b/test/lisp/emacs-lisp/subr-x-tests.el=0A@@=20-592,13=20+592,21=20@@=20= subr-string-fill=0A=20=20=20(should=20(equal=20(string-fill=20"foo=20bar=20= zot"=205)=20"foo\nbar\nzot"))=0A=20=20=20(should=20(equal=20(string-fill=20= "foo=20bar=20zot"=207)=20"foo=20bar\nzot")))=0A=20=0A-(ert-deftest=20= subr-string-limit=20()=0A-=20=20(should=20(equal=20(string-limit=20"foo"=20= 10)=20"foo"))=0A-=20=20(should=20(equal=20(string-limit=20"foo"=202)=20= "fo"))=0A-=20=20(should=20(equal=20(string-limit=20"foo"=202=20t)=20= "oo"))=0A-=20=20(should=20(equal=20(string-limit=20"abc"=2010=20t)=20= "abc"))=0A-=20=20(should=20(equal=20(string-limit=20"foo"=200)=20""))=0A= -=20=20(should-error=20(string-limit=20"foo"=20-1)))=0A+(ert-deftest=20= subr-string-prefix=20()=0A+=20=20(should=20(equal=20(string-prefix=20= "abc"=204)=20"abc"))=0A+=20=20(should=20(equal=20(string-prefix=20"abc"=20= 3)=20"abc"))=0A+=20=20(should=20(equal=20(string-prefix=20"abc"=202)=20= "ab"))=0A+=20=20(should=20(equal=20(string-prefix=20"abc"=201)=20"a"))=0A= +=20=20(should=20(equal=20(string-prefix=20"abc"=200)=20""))=0A+=20=20= (should-error=20(string-prefix=20"abc"=20-1)))=0A+=0A+(ert-deftest=20= subr-string-suffix=20()=0A+=20=20(should=20(equal=20(string-suffix=20= "abc"=204)=20"abc"))=0A+=20=20(should=20(equal=20(string-suffix=20"abc"=20= 3)=20"abc"))=0A+=20=20(should=20(equal=20(string-suffix=20"abc"=202)=20= "bc"))=0A+=20=20(should=20(equal=20(string-suffix=20"abc"=201)=20"c"))=0A= +=20=20(should=20(equal=20(string-suffix=20"abc"=200)=20""))=0A+=20=20= (should-error=20(string-suffix=20"abc"=20-1)))=0A=20=0A=20(ert-deftest=20= subr-string-lines=20()=0A=20=20=20(should=20(equal=20(string-lines=20= "foo")=20'("foo")))=0A--=20=0A2.21.1=20(Apple=20Git-122.3)=0A=0A= --Apple-Mail=_0B559A6D-71A9-42FE-9F5A-8A4568B01810--