Szűrő (magasabb rendű funkció) - Filter (higher-order function)

A funkcionális programozás során a szűrő egy magasabb rendű függvény, amely valamilyen adatstruktúrát (általában listát ) dolgoz fel valamilyen célból, hogy új adatstruktúrát hozzon létre, amely pontosan azokat az elemeket tartalmazza az eredeti adatszerkezetből, amelyekre egy adott predikátum visszaadja a logikai értéket true .

Példa

A Haskell , a kód például

 filter even [1..10]

kiértékeli a 2, 4,…, 10 listát úgy, hogy az predikátumot evenaz 1, 2,…, 10 egész számok listájának minden elemére alkalmazza ebben a sorrendben, és létrehoz egy új listát azokról az elemekről, amelyekre a predikátum visszaadja a true logikai értéket , ezáltal olyan listát adva, amely csak a lista páros tagjait tartalmazza. Fordítva, a kód példa

 filter (not . even) [1..10]

kiértékeli az 1, 3,…, 9 listára az 1, 2,…, 10 egész számok listájának azon elemeinek összegyűjtésével, amelyekre a predikátum evenhamis logikai értéket ad vissza ( .a függvényösszetétel -operátorral ).

Vizuális példa

Az alábbiakban megtekintheti a szűrési folyamat egyes lépéseinek nézetét X = [0, 5, 8, 3, 2, 1]a függvény szerinti egész számok listájához :

Ez a függvény azt fejezi ki, hogy ha még a visszatérési érték is , akkor egyébként . Ez a predikátum.

szűrőfunkciós feldolgozási lépések alkalmazása
A feldolgozási lépések nézete a szűrőfunkció listán történő alkalmazásakor

Nyelvi összehasonlítás

A szűrő szabványos funkció sok programozási nyelvhez , pl. Haskell, OCaml , Standard ML vagy Erlang . A Common Lisp biztosítja a funkciókat remove-ifés remove-if-not. A Scheme Requests for Implementation (SRFI) 1 megvalósítja a nyelvi séma szűrőjének megvalósítását . A C ++ biztosítja az algoritmusokat remove_if (mutáló) és remove_copy_if(nem mutáló); A C ++ 11 ezenkívül biztosítja copy_if(nem mutáló). A Smalltalk biztosítja a select:módszert a gyűjteményekhez. A szűrő az őket támogató nyelvek listájának megértésével is megvalósítható .

Haskellben a filterkövetkezőképpen valósítható meg:

 filter :: (a -> Bool) -> [a] -> [a]
 filter _ []     = []
 filter p (x:xs) = [x | p x] ++ filter p xs

Itt []az üres listát, ++a listafűzési műveletet [x | p x]jelöli , és feltételesen értéket tartalmazó listát jelöl x, ha a feltétel p xérvényes (értékeli a True) értéket.

Szűrés különböző nyelveken
Nyelv Szűrő Megjegyzések
APL (pred array)/array
vagy
pred{⍵/⍨⍺⍺ ⍵}array
A második példa egy APL dop .
C# 3.0 ienum.Where(pred)
vagy
A wherezáradék
Hol van egy kiterjesztési módszer, az
ienum egy IEnumerable
Hasonlóan minden .NET nyelven
CFML obj.filter(func) Hol objvan tömb vagy szerkezet. A funcargumentumként fogadja az egyes elemek értékét.
Clojure (filter predicate list) Vagy a lista megértése révén :(for [x list :when (pred x)] x)
Közös Lisp (remove-if inverted-pred list)
(remove-if (complement pred) list)
(remove-if-not pred list)
A függvény remove-if-notelavult az egyenértékű javára, remove-ifahol a predikátum kiegészül. Így a szűrőt (remove-if-not #'oddp '(0 1 2 3))meg kell írni, (remove-if (complement #'oddp) '(0 1 2 3))vagy egyszerűbben: (remove-if #'evenp '(0 1 2 3))ahol evenpvisszaadja a fordított értékét oddp.
C ++ std::remove_copy_if(begin, end, result, prednot)
std::copy_if(begin, end, result, pred) (C++11)
a fejléc <algoritmus>
kezdete , vége , eredménye az iterátorok
predikátusa megfordul
D std.algorithm.filter!(pred)(list)
Erlang lists:filter(Fun, List) Vagy a lista megértése révén :[ X || X <- List, Fun(X) ]
Groovy list.findAll(pred)
Haskell filter pred list Vagy a lista megértése révén :[x | x <- list, pred x]
Haxe list.filter(pred)
Lambda.filter(list, pred)
Vagy a lista megértése révén :[x | x <- list, pred x]
J (#~ pred) list Példa a monádikus horogra. # másolás, ~ megfordítja az érveket.(f g) y = y f (g y)
Julia filter(pred, array) A szűrő funkció dictadattípust is elfogad . Vagy a lista megértése révén :[x for x in array if pred(x)]
Java 8+ stream.filter(pred)
JavaScript 1.6 array.filter(pred)
Kotlin array.filter(pred)
Mathematica Select[list, pred]
Objective-C ( Kakaó Mac OS X 10.4+ verzióban) [array filteredArrayUsingPredicate:pred] predegy NSPredicate objektum, amely korlátozott expresszivitással rendelkezik
F# , OCaml , Standard ML List.filter pred list
PARI/GP select(expr, list) Az érvek sorrendje a 2.4.2.
Perl grep block list
grep expr, list
PHP array_filter(array, pred)
Bevezető filter(+Closure,+List,-List) Az ISO/IEC 13211-1: 1995/Cor.2: 2012 óta az alapszabvány záró alkalmazást tartalmaz call/N
Piton filter(func, list) Vagy, via lista megértés : . A Python 3 -ban a lista helyett iterátort adtak vissza . A kiegészítő funkcionalitás, amely iterátort ad vissza azokra az elemekre, amelyekre a predikátum hamis, szintén elérhető a szabványos könyvtárban, mint a modulban. [x for x in list if pred(x)]filterfilterfalseitertools
Rubin enum.find_all {block}
enum.select {block}
enum egy felsorolás
Rozsda iterator.filter(pred) iteratoregy Iteratorés a filtermetódus új iterátort ad vissza; predegy olyan függvény (kifejezetten FnMut), amely megkapja az iterátor elemét, és visszaadja abool
S , R. Filter(pred,array)
array[pred(array)]
A második esetben, pred kell lennie vectorized funkció
Scala list.filter(pred) Vagy a megértés révén: for(x <- list; if pred) yield x
Séma R 6 RS (filter pred list)
(remove inverted pred list)
(partition pred list list)
Csevej aCollection select: aBlock
Gyors array.filter(pred)
filter(sequence, pred)
XPath , XQuery list[block]
filter(list, func)
A blockkontextusban az elem .az aktuális értéket tartalmazza

Változatok

A szűrő az eredeti lista módosítása nélkül hozza létre eredményét. Sok programozási nyelv olyan változatokat is kínál, amelyek romboló módon módosítják a lista argumentumot a gyorsabb teljesítmény érdekében. A szűrő egyéb változatai (pl. Haskell dropWhileés partition) szintén gyakoriak. A közös memória optimalizálás a tisztán funkcionális programozási nyelvek az, hogy a bemeneti listában, majd szűrjük eredményeként részesedése a leghosszabb közös farok ( tail-megosztás ).

Lásd még

Hivatkozások