Listabstraktion eller listförståelse i syntaxen för vissa programmeringsspråk är ett sätt att kompakt beskriva listbearbetningsoperationer [ 1] .
Listinkludering låter dig utvärdera oändliga listor (på språk som stöder dem). Till exempel, på Miranda- språket, kan en oändlig lista med jämna positiva tal skrivas enligt följande [1] :
[ n | n <- [ 1 .. ]; n rem 2 = 0 ]som lyder: "listan över alla n så att n är i [1..] och resten när n divideras med 2 är noll."
I analogi med listinneslutningar i andra programmeringsspråk finns det bitsträngsuttryck ( Erlang ), list- och ordboksinklusioner ( Python i version 3).
Översättningen av Field och Harrisons bok "Functional Programming" [1] introducerar termen "listabstraktion" och "listinkludering". Men i litteraturen används också "listuttryck", "listaval" [2] , "listinbäddning" [3] [4] , "listgenerator" (kanske inte en särskilt bra översättning, eftersom det i funktionell programmering finns en separat koncept för listgeneratorn, engelsk listgenerator [5] ) [6] , "listdeterminant" [7] .
I axiomatiken i Zermelo-Fraenkel-mängdteorin finns ett urvalsaxiom, som låter dig bygga en uppsättning baserat på den befintliga, genom att välja element som motsvarar något predikat. Listabstraktion är analogt med urval för listor [8] och ibland stöter man till och med på termen ZF-uttryck [9] .
Jämna tal från 2 till 9998 inklusive:
[ n för n i intervallet ( 1 , 10000 ) om n % 2 == 0 ]List include kan använda kapslade iterationer över variabler:
[( x , y ) för x i intervallet ( 1 , 10 ) för y i intervallet ( 1 , 10 ) om x % y == 0 ]Python har också generatoruttryck som har en syntax som liknar listförståelse men som returnerar en iterator [10] . Summan av de jämna talen från föregående exempel:
summa ( n för n i intervallet ( 1 , 10000 ) om n % 2 == 0 )I det här fallet behövs inga ytterligare parenteser, men i allmänhet kommer deras frånvaro att orsaka ett syntaxfel.
Som nämnts ovan tillhandahåller Python liknande faciliteter för att skapa uppsättningar och ordböcker.
>>> { x för x i intervallet ( 10 )} { 0 , 1 , 2 , 3 , 4 , 5 , 6 , 7 , 8 , 9 } >>> { x : x ** 2 för x i intervallet ( 10 )} { 0 : 0 , 1 : 1 , 2 : 4 , 3 : 9 , 4 : 16 , 5 : 25 , 6 : 36 , 7 : 49 , 8 : 64 , 9 : 81 }Jämna tal från 2 till 9998 inklusive:
( 1 ... 10 000 ) . välj { | jag | i % 2 == 0 } # med en implicit to_proc-metod anropa :even-symbolen? ( 1 ... 10 000 ) . välj ( & :even? )I Erlang skulle listgeneratorn se ut så här:
[ N || N <- [ 1 , 2 , 3 , 4 , 5 , 6 ], N rem2 == 0 ] .Exempel med jämna tal i Haskell [8] :
[ x | x <- [ 1 .. ], x ` mod ` 2 == 0 ] -- oändlig lista: [2,4,6,8,10..]Hos Haskell kallas ett uttryck av ett slag x <- вырför en generator . Det kan finnas flera generatorer i ett urval:
[( x , y ) | x <- [ 1 .. 4 ], y <- [ 1 .. 4 ], x ` mod ` y == 0 ] -- 8 unika par: [(1,1),(2,1),(2) ,2),(3,1),(3,3),(4,1),(4,2),(4,4)]LINQ för C# 3.0 har flera listliknande syntaxer för frågeuttryck [11] :
var s = Enumerable . Område ( 0 , 100 ). Där ( x => x * x > 3 ). Välj ( x => x * 2 );Alternativ syntax, som påminner om SQL :
var s = från x i Enumerable . Område ( 0 , 100 ) där x * x > 3 välj x * 2 ;Syntaxen för listförståelse i Julia är lånad från Python.
Exempel med en lista med jämna tal:
[ n för n i 1 : 1000 om är jämnt ( n )]Liknande syntax används för att fylla i andra typer av behållare:
# Tuppel tuppel ( n ^ 2 för n i - 10 : 10 ) # set Set ( abs ( n ) för n in - 10 : 10 ) # Diktordbok ( c => kodpunkt ( c ) för c i 'a' : 'z' )Som i Python stöds kapslad iteration över flera variabler:
julia > [( x , y ) för x i 1 : 3 för y i 1 : 3 om x ≠ y ] 6 - element Array { Tuple { Int64 , Int64 }, 1 } : ( 1 , 2 ) ( 1 , 3 ) ( 2 , 1 ) ( 2 , 3 ) ( 3 , 1 ) ( 3 , 2 )