问题
I'm just starting out with scala here and I'm finding some of the syntax confusing. For example from the scalatest main page
class ExampleSpec extends FlatSpec with Matchers {
"A Stack" should "pop values in last-in-first-out order" in {...}
}
As I read it that means "should" is a method of string "A stack"? If that is right, how does that happen? It doesn't seem to work from the scala prompt
scala> class ExampleSpec {
| "A Stack" should "pop values"
| }
<console>:9: error: value should is not a member of String
"A Stack" should "pop values"
If "should" is not a method of string "A Stack" in the above snippet then how am I to read the snippet correctly? What is "should" and how does it relate to the string? Any clues?
回答1:
This is commonly known as the Pimp My Library Enrich My Library pattern where we can extend other libraries (in this case Scala strings) with our own methods by using implicit conversions.
The way it works is that FlatSpec
mixes in a trait called ShouldVerb
which has the following implicit conversion defined:
implicit def convertToStringShouldWrapper(o: String): StringShouldWrapperForVerb =
new StringShouldWrapperForVerb {
val leftSideString = o.trim
}
And StringShouldWrapperForVerb
has the should
method defined:
def should(right: String) ....
The reason it does not work in the REPL for you is that you don't have FlatSpec
and via that the ShouldVerb
trait mixed in.
You can read more about this in the documentation under implicit classes.
回答2:
In org.scalatest.Matchers
, an implicit conversion is provided that converts String
to StringShouldWrapper
, which is the class that provides the should
function on String
:
implicit def convertToStringShouldWrapper(o: String): StringShouldWrapper
The compiler will implicitly convert any String
to a StringShouldWrapper
when it encounters that call. If you call a function on an object that doesn't exist, the compiler will check in-scope implicit conversions (like the one above) to see if any of them will provide that function.
来源:https://stackoverflow.com/questions/30757722/scalatest-a-stack-should-do-something-wtf-how-is-should-a-method-of-stri