2013-10-31 247 views
4

我已經編寫了下面的代碼來檢查字符串是否包含特殊字符。代碼對我來說看起來太複雜了,但我不知道如何簡化它。有任何想法嗎?Scala檢查字符串是否包含特殊字符

def containsNoSpecialChars(string: String): Boolean = { 
    val pattern = "^[a-zA-Z0-9]*$".r 
    return pattern.findAllIn(string).mkString.length == string.length 
}             //> containsNoSpecialChars: (string: String)Boolean 

containsNoSpecialChars("bl!a ")     //> res0: Boolean = false 
containsNoSpecialChars("bla9")     //> res1: Boolean = true 
+2

BTW,我發現很難與謂詞的工作,告訴是否有**不**。恕我直言更好的將是扭轉的邏輯和名稱的東西containsSpecialChars或離開邏輯是並命名它containsOnlyValidChars – Ingo

+0

這是正確的,感謝您的建議,我會改變它。 – MeiSign

回答

9
scala> val ordinary=(('a' to 'z') ++ ('A' to 'Z') ++ ('0' to '9')).toSet 
ordinary: scala.collection.immutable.Set[Char] = Set(E, e, X, s, x, 8, 4, n, 9, N, j, y, T, Y, t, J, u, U, f, F, A, a, 5, m, M, I, i, v, G, 6, 1, V, q, Q, L, b, g, B, l, P, p, 0, 2, C, H, c, W, h, 7, r, K, w, R, 3, k, O, D, Z, o, z, S, d) 

scala> def isOrdinary(s:String)=s.forall(ordinary.contains(_)) 
isOrdinary: (s: String)Boolean 


scala> isOrdinary("abc") 
res4: Boolean = true 

scala> isOrdinary("abc!") 
res5: Boolean = false 

我使用的設置,正確的選擇邏輯,但它也應該有一個載體,它可以避免你在看的亂七八糟的字母工作...

+0

令人印象深刻!我將實施該解決方案,謝謝! – MeiSign

+0

請原諒命名倒置。我認爲它使事情更清晰... –

+0

非常好的解決方案。 – user3341078

10

它使用Java字符串:

word.matches("^[a-zA-Z0-9]*$") 

,或者如果你不想處理正則表達式一個通過使用可以從Scala的RichString受益:

word.forall(_.isLetterOrDigit) 

或:

!word.exists(!_.isLetterOrDigit) 
+0

當我使用java字符串而不是scala字符串時,是否有任何缺點? – MeiSign

+0

根據此http://docs.oracle.com/javase/6/docs/api/java/lang/String.html,這相當於Pattern.matches(regex,str)。它們是相同的,因爲Scala RichString屬於正則表達式操作的Java類。 –

+2

這種方法有一個(小的)缺點,但是你的代碼也會受到影響:每次你想檢查一個字符串時,都會編譯這個模式。稍微更優化的解決方案是編譯模式並將其存儲爲類或對象字段。 –

6
def containsNoSpecialChars(string: String) = string.matches("^[a-zA-Z0-9]*$") 
相關問題