F # - tablice

Tablice to zmienne kolekcje o stałym rozmiarze, liczone od zera, kolejnych elementów danych, które są tego samego typu.

Tworzenie tablic

Możesz tworzyć tablice przy użyciu różnych składni i sposobów lub używając funkcji z modułu Array. W tej sekcji omówimy tworzenie tablic bez korzystania z funkcji modułu.

Istnieją trzy syntaktyczne sposoby tworzenia tablic bez funkcji -

  • Wymieniając kolejne wartości między [| i |] i oddzielone średnikami.
  • Umieszczając każdy element w osobnym wierszu, w takim przypadku separator średnika jest opcjonalny.
  • Używając wyrażeń sekwencyjnych.

Dostęp do elementów tablicy można uzyskać za pomocą operatora kropki (.) I nawiasów kwadratowych ([i]).

Poniższy przykład demonstruje tworzenie tablic -

//using semicolon separator
let array1 = [| 1; 2; 3; 4; 5; 6 |]
for i in 0 .. array1.Length - 1 do
   printf "%d " array1.[i]
printfn" "

// without semicolon separator
let array2 =
   [|
      1
      2
      3
      4
      5
   |]
for i in 0 .. array2.Length - 1 do
   printf "%d " array2.[i]
printfn" "

//using sequence
let array3 = [| for i in 1 .. 10 -> i * i |]
for i in 0 .. array3.Length - 1 do
   printf "%d " array3.[i]
printfn" "

Kiedy kompilujesz i wykonujesz program, daje to następujące dane wyjściowe -

1 2 3 4 5 6
1 2 3 4 5
1 4 9 16 25 36 49 64 81 100

Podstawowe operacje na tablicach

Moduł biblioteki Microsoft.FSharp.Collections.Array obsługuje operacje na tablicach jednowymiarowych.

W poniższej tabeli przedstawiono podstawowe operacje na tablicach -

Wartość Opis
dołącz: „T [] →„ T [] → „T []” Tworzy tablicę zawierającą elementy jednej tablicy, po których następują elementy innej tablicy.
średnia: ^ T [] → ^ T Zwraca średnią elementów w tablicy.
średnia Przez: ('T → ^ U) →' T [] → ^ U Zwraca średnią z elementów wygenerowanych przez zastosowanie funkcji do każdego elementu tablicy.
blit: 'T [] → int →' T [] → int → int → unit Odczytuje zakres elementów z jednej tablicy i zapisuje je w innej.
wybierz: ('T → opcja U) →' T [] → 'U [] Stosuje podaną funkcję do każdego elementu tablicy. Zwraca tablicę zawierającą wyniki x dla każdego elementu, dla którego funkcja zwraca Some (x).
zbierać: ('T →' U []) → T [] → 'U [] Stosuje podaną funkcję do każdego elementu tablicy, konkatenuje wyniki i zwraca połączoną tablicę.
concat: seq <'T []> →' T [] Tworzy tablicę zawierającą elementy każdej z podanych sekwencji tablic.
kopia: „T →” T [] Tworzy tablicę zawierającą elementy podanej tablicy.
utwórz: int → 'T →' T [] Tworzy tablicę, której wszystkie elementy są początkowo podaną wartością.
pusty: „T [] Zwraca pustą tablicę podanego typu.
istnieje: ('T → bool) →' T [] → bool Testuje, czy dowolny element tablicy spełnia podany predykat.
istnieje2: ('T1 →' T2 → bool) → 'T1 [] →' T2 [] → bool Testuje, czy dowolna para odpowiednich elementów dwóch tablic spełnia podany warunek.
wypełnienie: 'T [] → int → int →' T → unit Wypełnia zakres elementów tablicy podaną wartością.
filtr: ('T → bool) →' T [] → 'T [] Zwraca kolekcję zawierającą tylko elementy podanej tablicy, dla których zwraca podany warunek true.
znajdź: ('T → bool) →' T [] → 'T Zwraca pierwszy element, dla którego zwraca podana funkcja true. Podnosi KeyNotFoundException, jeśli taki element nie istnieje.
findIndex: ('T → bool) →' T [] → int Zwraca indeks pierwszego elementu w tablicy, który spełnia podany warunek. Podnosi KeyNotFoundException, jeśli żaden z elementów nie spełnia warunku.
fold: („Stan →„ T → ”Stan) →„ Stan → „T [] →„ Stan Stosuje funkcję do każdego elementu tablicy, tworząc wątek argumentu akumulatora przez obliczenia. Jeśli funkcją wejściową jest f, a elementy tablicy to i0 ... iN, ta funkcja oblicza f (... (fs i0) ...) iN.
fold2: ('Stan →' T1 → 'T2 →' Stan) → 'Stan →' T1 [] → 'T2 [] →' Stan Stosuje funkcję do par elementów z dwóch dostarczonych tablic, od lewej do prawej, tworząc wątek argumentu akumulatora przez obliczenia. Dwie tablice wejściowe muszą mieć takie same długości; w przeciwnym razie zostanie zgłoszony ArgumentException.
foldBack: ('T →' Stan → 'Stan) →' T [] → 'Stan →' Stan Stosuje funkcję do każdego elementu tablicy, tworząc wątek argumentu akumulatora przez obliczenia. Jeśli funkcją wejściową jest f, a elementy tablicy to i0 ... iN, ta funkcja oblicza f i0 (... (f iN s)).
foldBack2: ('T1 →' T2 → 'Stan →' Stan) → 'T1 [] →' T2 [] → 'Stan →' Stan Stosuje funkcję do par elementów z dwóch dostarczonych tablic, od prawej do lewej, tworząc wątek argumentu akumulatora przez obliczenia. Dwie tablice wejściowe muszą mieć takie same długości; w przeciwnym razie zostanie zgłoszony ArgumentException.
forall: ('T → bool) →' T [] → bool Testuje, czy wszystkie elementy tablicy spełniają podany warunek.
forall2: ('T1 →' T2 → bool) → 'T1 [] →' T2 [] → bool Testuje, czy wszystkie odpowiadające elementy dwóch dostarczonych tablic spełniają podany warunek.
get: 'T [] → int →' T Pobiera element z tablicy.
init: int → (int → 'T) →' T [] Używa podanej funkcji, aby utworzyć tablicę podanego wymiaru.
isEmpty: 'T [] → bool Sprawdza, czy tablica zawiera jakieś elementy.
iter: ('T → jednostka) →' T [] → jednostka Stosuje podaną funkcję do każdego elementu tablicy.
iter2: ('T1 →' T2 → jednostka) → 'T1 [] →' T2 [] → jednostka) Stosuje podaną funkcję do pary elementów z pasujących indeksów w dwóch tablicach. Dwie tablice muszą mieć takie same długości; w przeciwnym razie zostanie zgłoszony ArgumentException.
iteri: (int → 'T → jednostka) →' T [] → jednostka Stosuje podaną funkcję do każdego elementu tablicy. Liczba całkowita przekazana do funkcji wskazuje indeks elementu.
iteri2: (int → 'T1 →' T2 → jednostka) → 'T1 [] →' T2 [] → jednostka Stosuje podaną funkcję do pary elementów z pasujących indeksów w dwóch tablicach, przekazując również indeks elementów. Dwie tablice muszą mieć takie same długości; w przeciwnym razie zostanie zgłoszony ArgumentException.
długość: „T [] → int Zwraca długość tablicy. Właściwość Length robi to samo.
mapa: ('T →' U) → 'T [] →' U [] Tworzy tablicę, której elementy są wynikiem zastosowania dostarczonej funkcji do każdego z elementów dostarczonej tablicy.
map2: ('T1 →' T2 → 'U) →' T1 [] → 'T2 [] →' U [] Tworzy tablicę, której elementy są wynikiem zastosowania dostarczonej funkcji do odpowiednich elementów dwóch dostarczonych tablic. Dwie tablice wejściowe muszą mieć takie same długości; w przeciwnym razie zostanie zgłoszony ArgumentException.
mapi: (int → 'T →' U) → 'T [] →' U [] Tworzy tablicę, której elementy są wynikiem zastosowania dostarczonej funkcji do każdego z elementów dostarczonej tablicy. Indeks w postaci liczby całkowitej przekazany do funkcji wskazuje indeks transformowanego elementu.
mapi2: (int → 'T1 →' T2 → 'U) →' T1 [] → 'T2 [] →' U [] Tworzy tablicę, której elementy są wynikiem zastosowania dostarczonej funkcji do odpowiednich elementów dwóch kolekcji parami, przekazując również indeks elementów. Dwie tablice wejściowe muszą mieć takie same długości; w przeciwnym razie zostanie zgłoszony ArgumentException.
max: „T [] →„ T Zwraca największy ze wszystkich elementów tablicy. Operators.max służy do porównywania elementów.
maxBy: ('T →' U) → 'T [] →' T Zwraca największy ze wszystkich elementów tablicy, porównany za pomocą Operators.max w wyniku funkcji.
min: ('T [] →' T Zwraca najmniejszy ze wszystkich elementów tablicy. Operators.min służy do porównywania elementów.
minBy: ('T →' U) → 'T [] →' T Zwraca najmniejszy ze wszystkich elementów tablicy. Operators.min służy do porównywania elementów.
ofList: 'T lista →' T [] Tworzy tablicę z podanej listy.
ofSeq: seq <'T> →' T [] Tworzy tablicę z podanego wyliczalnego obiektu.
partycja: ('T → bool) →' T [] → 'T [] *' T [] Dzieli tablicę na dwie tablice, z których jedna zawiera elementy, dla których zwraca podany warunek true, a drugi zawierający te, dla których wraca false.
permute: (int → int) → 'T [] →' T [] Permutuje elementy tablicy zgodnie z określoną permutacją.
wybierz: (opcja 'T →' U) → 'T [] →' U Stosuje podaną funkcję do kolejnych elementów podanej tablicy, zwracając pierwszy wynik, gdy funkcja zwraca Some (x) dla niektórych x. Jeśli funkcja nigdy nie zwraca Some (x), zgłaszany jest wyjątek KeyNotFoundException.
zmniejsz: ('T →' T → 'T) →' T [] → 'T Stosuje funkcję do każdego elementu tablicy, tworząc wątek argumentu akumulatora przez obliczenia. Jeśli funkcją wejściową jest f, a elementy tablicy to i0 ... iN, ta funkcja oblicza f (... (f i0 i1) ...) iN. Jeśli tablica ma rozmiar zero, zostanie zgłoszony ArgumentException.
redukcjaBack: ('T →' T → 'T) →' T [] → 'T Stosuje funkcję do każdego elementu tablicy, tworząc wątek argumentu akumulatora przez obliczenia. Jeśli funkcją wejściową jest f, a elementy to i0 ... iN, funkcja ta oblicza f i0 (... (f iN-1 iN)). Jeśli tablica ma rozmiar zero, zostanie zgłoszony ArgumentException.
rev: 'T [] →' T [] Odwraca kolejność elementów w podanej tablicy.
skanowanie: ('Stan →' T → 'Stan) →' Stan → 'T [] →' Stan []) Zachowuje się jak spasowanie, ale zwraca wyniki pośrednie wraz z wynikami końcowymi.
scanBack: ('T →' Stan → 'Stan) →' T [] → 'Stan →' Stan [] Zachowuje się jak foldBack, ale zwraca wyniki pośrednie wraz z wynikami końcowymi.
zestaw: 'T [] → int →' T → jednostka Ustawia element tablicy.
sortuj: 'T [] →' T [] Sortuje elementy tablicy i zwraca nową tablicę. Operators.compare służy do porównywania elementów.
sortBy: („T →” Klucz) → „T [] →„ T [] ” Sortuje elementy tablicy przy użyciu dostarczonej funkcji, aby przekształcić elementy do typu, na którym oparta jest operacja sortowania, i zwraca nową tablicę. Operators.compare służy do porównywania elementów.
sortInPlace: 'T [] → jednostka Sortuje elementy tablicy, zmieniając tablicę w miejscu, używając podanej funkcji porównania. Operators.compare służy do porównywania elementów.
sortInPlaceBy: (klawisz „T →”) → „T [] → jednostka Sortuje elementy tablicy, zmieniając tablicę w miejscu, używając dostarczonej projekcji dla kluczy. Operators.compare służy do porównywania elementów.
sortInPlaceWith: ('T →' T → int) → 'T [] → jednostka Sortuje elementy tablicy przy użyciu podanej funkcji porównania, aby zmienić tablicę w miejscu.
sortWith: ('T →' T → int) → 'T [] →' T [] Sortuje elementy tablicy przy użyciu podanej funkcji porównującej i zwraca nową tablicę.
sub: 'T [] → int → int →' T [] Tworzy tablicę zawierającą podany podzakres, który jest określony przez początkowy indeks i długość.
suma: 'T [] → ^ T Zwraca sumę elementów w tablicy.
sumBy: ('T → ^ U) →' T [] → ^ U Zwraca sumę wyników wygenerowanych przez zastosowanie funkcji do każdego elementu tablicy.
toList: „T [] →” T lista Konwertuje podaną tablicę na listę.
toSeq: 'T [] → seq <' T> Wyświetla podaną tablicę jako sekwencję.
tryFind: ('T → bool) →' T [] → 'T opcja Zwraca pierwszy element w podanej tablicy, dla którego podana funkcja zwraca true. ZwrotyNone jeśli taki element nie istnieje.
tryFindIndex: ('T → bool) →' T [] → opcja int Zwraca indeks pierwszego elementu w tablicy, który spełnia podany warunek.
tryPick: (opcja 'T →' U) → 'T [] → opcja' U Stosuje podaną funkcję do kolejnych elementów podanej tablicy i zwraca pierwszy wynik, w którym funkcja zwraca Some (x) dla niektórych x. Jeśli funkcja nigdy nie zwraca Some (x),None jest zwracany.
rozpakuj: ('T1 *' T2) [] → 'T1 [] *' T2 [] Dzieli tablicę par krotek na krotkę dwóch tablic.
unzip3: ('T1 *' T2 * 'T3) [] →' T1 [] * 'T2 [] *' T3 [] Dzieli tablicę krotek trzech elementów na krotkę trzech tablic.
zeroCreate: int → 'T [] Tworzy tablicę, której elementy są początkowo ustawione na wartość domyślną Unchecked.defaultof <'T>.
zip: 'T1 [] →' T2 [] → ('T1 *' T2) [] Łączy dwie tablice w tablicę krotek, które mają dwa elementy. Dwie tablice muszą mieć równe długości; w przeciwnym razie zostanie zgłoszony ArgumentException.
zip3: 'T1 [] →' T2 [] → 'T3 [] → (' T1 * 'T2 * 113' T3) [] Łączy trzy tablice w tablicę krotek, które mają trzy elementy. Trzy tablice muszą mieć równe długości; w przeciwnym razie zostanie zgłoszony ArgumentException.

W następnej sekcji zobaczymy zastosowania niektórych z tych funkcji.

Tworzenie tablic przy użyciu funkcji

Moduł Array udostępnia kilka funkcji, które tworzą tablicę od podstaw.

  • Plik Array.empty funkcja tworzy nową pustą tablicę.

  • Plik Array.create funkcja tworzy tablicę o określonym rozmiarze i ustawia wszystkie elementy na podane wartości.

  • Plik Array.init function tworzy tablicę, podając wymiar i funkcję do generowania elementów.

  • Plik Array.zeroCreate funkcja tworzy tablicę, w której wszystkie elementy są inicjalizowane do wartości zerowej.

  • Plik Array.copy function tworzy nową tablicę, która zawiera elementy, które są kopiowane z istniejącej tablicy.

  • Plik Array.sub funkcja generuje nową tablicę z podzakresu tablicy.

  • Plik Array.append function tworzy nową tablicę, łącząc dwie istniejące tablice.

  • Plik Array.choose funkcja wybiera elementy tablicy do włączenia do nowej tablicy.

  • Plik Array.collect function uruchamia określoną funkcję na każdym elemencie tablicy istniejącej tablicy, a następnie zbiera elementy wygenerowane przez funkcję i łączy je w nową tablicę.

  • Plik Array.concat funkcja pobiera sekwencję tablic i łączy je w jedną tablicę.

  • Plik Array.filter function przyjmuje logiczną funkcję warunkową i generuje nową tablicę, która zawiera tylko te elementy z tablicy wejściowej, dla których warunek jest prawdziwy.

  • Plik Array.rev funkcja generuje nową tablicę, odwracając kolejność istniejącej tablicy.

Poniższe przykłady demonstrują te funkcje -

Przykład 1

(* using create and set *)
let array1 = Array.create 10 ""
for i in 0 .. array1.Length - 1 do
   Array.set array1 i (i.ToString())
for i in 0 .. array1.Length - 1 do
   printf "%s " (Array.get array1 i)
printfn " "

(* empty array *)
let array2 = Array.empty
printfn "Length of empty array: %d" array2.Length

let array3 = Array.create 10 7.0
printfn "Float Array: %A" array3

(* using the init and zeroCreate *)
let array4 = Array.init 10 (fun index -> index * index)
printfn "Array of squares: %A" array4

let array5 : float array = Array.zeroCreate 10
let (myZeroArray : float array) = Array.zeroCreate 10
printfn "Float Array: %A" array5

Kiedy kompilujesz i wykonujesz program, daje to następujące dane wyjściowe -

0 1 2 3 4 5 6 7 8 9
Length of empty array: 0
Float Array: [|7.0; 7.0; 7.0; 7.0; 7.0; 7.0; 7.0; 7.0; 7.0; 7.0|]
Array of squares: [|0; 1; 4; 9; 16; 25; 36; 49; 64; 81|]
Float Array: [|0.0; 0.0; 0.0; 0.0; 0.0; 0.0; 0.0; 0.0; 0.0; 0.0|]

Przykład 2

(* creating subarray from element 5 *)
(* containing 15 elements thereon *)

let array1 = [| 0 .. 50 |]
let array2 = Array.sub array1 5 15
printfn "Sub Array:"
printfn "%A" array2

(* appending two arrays *)
let array3 = [| 1; 2; 3; 4|]
let array4 = [| 5 .. 9 |]
printfn "Appended Array:"
let array5 = Array.append array3 array4
printfn "%A" array5

(* using the Choose function *)
let array6 = [| 1 .. 20 |]
let array7 = Array.choose (fun elem -> if elem % 3 = 0 then
   Some(float (elem))
      else
   None) array6

printfn "Array with Chosen elements:"
printfn "%A" array7

(*using the Collect function *)
let array8 = [| 2 .. 5 |]
let array9 = Array.collect (fun elem -> [| 0 .. elem - 1 |]) array8
printfn "Array with collected elements:"
printfn "%A" array9

Kiedy kompilujesz i wykonujesz program, daje to następujące dane wyjściowe -

Sub Array:
[|5; 6; 7; 8; 9; 10; 11; 12; 13; 14; 15; 16; 17; 18; 19|]
Appended Array:
[|1; 2; 3; 4; 5; 6; 7; 8; 9|]
Array with Chosen elements:
[|3.0; 6.0; 9.0; 12.0; 15.0; 18.0|]
Array with collected elements:
[|0; 1; 0; 1; 2; 0; 1; 2; 3; 0; 1; 2; 3; 4|]

Przeszukiwanie tablic

Plik Array.find function przyjmuje funkcję logiczną i zwraca pierwszy element, dla którego funkcja zwraca wartość true, w przeciwnym razie zgłasza wyjątek KeyNotFoundException.

Plik Array.findIndex funkcja działa podobnie, z tą różnicą, że zwraca indeks elementu zamiast samego elementu.

Poniższy przykład ilustruje to.

Microsoft podaje ten ciekawy przykład programu, który wyszukuje pierwszy element w zakresie podanej liczby, który jest zarówno idealnym kwadratem, jak i idealną kostką -

let array1 = [| 2 .. 100 |]
let delta = 1.0e-10
let isPerfectSquare (x:int) =
   let y = sqrt (float x)
   abs(y - round y) < delta

let isPerfectCube (x:int) =
   let y = System.Math.Pow(float x, 1.0/3.0)
   abs(y - round y) < delta

let element = Array.find (fun elem -> isPerfectSquare elem && isPerfectCube elem) array1

let index = Array.findIndex (fun elem -> isPerfectSquare elem && isPerfectCube elem) array1

printfn "The first element that is both a square and a cube is %d and its index is %d." element index

Kiedy kompilujesz i wykonujesz program, daje to następujące dane wyjściowe -

The first element that is both a square and a cube is 64 and its index is 62.