2010-08-04 6 views
8

Dans mon application, je filtrer un tableau de fichiers par divers types, comme ce qui suit:méthode Scala qui retourne plusieurs fonctions de filtre concaténés

val files:Array[File] = recursiveListFiles(file) 
    .filter(!_.toString.endsWith("png")) 
    .filter(!_.toString.endsWith("gif")) 
    .filter(!_.toString.endsWith("jpg")) 
    .filter(!_.toString.endsWith("jpeg")) 
    .filter(!_.toString.endsWith("bmp")) 
    .filter(!_.toString.endsWith("db")) 

Mais il serait plus soigneusement de définir une méthode qui prend String array et renvoie tous ces filtres en tant que fonction concaténée. Est-ce possible? Alors que je peux écrire

val files:Array[File] = recursiveListFiles(file).filter(
    notEndsWith("png", "gif", "jpg", "jpeg", "bmp", "db") 
) 

Répondre

10

Vous pourriez faire quelque chose comme ceci:

def notEndsWith(suffix: String*): File => Boolean = { file => 
    !suffix.exists(file.getName.endsWith) 
} 
+1

+1 c'est la raison pour laquelle j'aime Scala – onof

+3

Nice, bien que j'implémente probablement "endsWith" plutôt que "notEndsWith", en règle générale. Si vous implémentez "notEndsWith" et avez réellement besoin de "endsWith", vous finissez par coder comme! NotEndsWith, ce qui est source de confusion en raison du double négatif. Définir les conditions positivement est plus important avec la programmation fonctionnelle, car la densité supplémentaire des constructions fonctionnelles exige une attention particulière à la clarté de l'expression –

1

Une façon serait quelque chose comme ceci:

def notEndsWith(files:Array[File], exts:String*) = 
    for(file <- files; if !exts.exists(file.toString.endsWith(_))) yield file 

Ce qui pourrait être appelé comme ceci:

val files = Array(new File("a.png"),new File("a.txt"),new File("a.jpg")) 
val filtered = notEndsWith(files, "png", "jpg").toList