Hi Richard, (CC squeak-dev list, replies to the relevant list please) On Thu, Apr 21, 2022 at 12:07:32AM +1200, Richard O'Keefe wrote:
I've just tracked down a nasty little problem porting some code to Pharo. As a result, I have added to the comments in my own versions of these methods. beginsWith: aSequence "Answer true if aSequence is a prefix of the receiver. This makes sense for all sequences. There is a compatibility issue concerning 'abc' beginsWith: '' + VisualWorks, Dolphin, astc, GNU ST (where the method is called #startsWith:) and VisualAge (where the method is called #wbBeginsWith:) agree than EVERY sequence begins with an empty prefix. - Squeak and Pharo agree that NO sequence begins with an empty sequence. # ST/X chooses compatibility with Squeak, heaving a big unhappy sigh, and adds #startsWith: to have something sensible to use. Now ST/X *thinks* it is compatible with VW, though it isn't, so I wonder if this was a bug that VW fixed and Squeak didn't? astc goes with the majority here. This is also compatible with Haskell, ML, and with StartsWith in C# and startsWith in Java." ^self beginsWith: aSequence ignoringCase: false
endsWith: aSequence "Answer true if aSequence is a suffix of the receiver. This makes sense for all sequences. There is a compatibility issue concerning 'abc' endsWith: ''. + VisualWorks, Dolphin, astc, GNU ST, and VisualAge (where the method is called #wbEndsWith:) agree that EVERY sequence ends with an empty suffix. - Squeak and Pharo agree that NO sequence ends with an empty suffix. # ST/X chooses compatibility with the majority, apparently unaware that this makes #beginsWith: and #endsWith: inconsistent. astc goes with the majority here. This is also compatible with Haskell, ML, C#, and Java." ^self endsWith: aSequence ignoringCase: false
Does anyone have any idea - why Squeak and Pharo are the odd ones out? - why anyone thought making #beginsWith: and #endsWith:, um, "quirky" was a good idea (it's pretty standard in books on the theory of strings to define "x is a prefix of y iff there is a z such that y = x concatenated with z")
The Squeak behavior was introduced in November 1998 by Dan Ingalls in conjunction with some VM improvements that he was doing, and was included in the Squeak2.2 release at that time. Prior to that update, Squeak did this: 'abc' beginsWith: '' ==> true 'abc' endsWith: '' ==> true For Squeak2.2 and later it is: 'abc' beginsWith: '' ==> false 'abc' endsWith: '' ==> false Pharo presumably inherits this from Squeak. I am attaching Dan's original change set from the early Squeak update stream so you can see the context. The change set comment says that "endsWith:, beginsWith:, and match have been rewritten to take advantage of this considerably faster method" (referring to a new primitive that Dan had added to the VM in this change set).
I was about to try to file a bug report for the first time, then realised that maybe other people don't think this IS a bug.
I don't think it is a bug. I can't think of a case where it makes sense to say that a string of characters "begins with" or "ends with" a string that contains nothing. In any case, that's the history of the change in Squeak and Pharo as best as I can reconstruct it. HTH, Dave