Catatan
Akses ke halaman ini memerlukan otorisasi. Anda dapat mencoba masuk atau mengubah direktori.
Akses ke halaman ini memerlukan otorisasi. Anda dapat mencoba mengubah direktori.
F# 6 menambahkan beberapa peningkatan pada bahasa F# dan F# Interactive. Ini dirilis dengan .NET 6.
Anda dapat mengunduh .NET SDK terbaru dari halaman unduhan .NET.
Get started
F# 6 tersedia di semua distribusi .NET Core dan alat Visual Studio. Untuk informasi selengkapnya, lihat Mulai menggunakan F#.
tugas {...}
F# 6 menyertakan dukungan asli untuk menulis tugas .NET dalam kode F# menggunakan ekspresi tugas. Ekspresi tugas mirip dengan ekspresi asinkron tetapi memungkinkan Anda menulis tugas .NET secara langsung.
Misalnya, pertimbangkan kode F# berikut untuk membuat tugas yang kompatibel dengan .NET.
let readFilesTask (path1, path2) =
async {
let! bytes1 = File.ReadAllBytesAsync(path1) |> Async.AwaitTask
let! bytes2 = File.ReadAllBytesAsync(path2) |> Async.AwaitTask
return Array.append bytes1 bytes2
} |> Async.StartAsTask
Menggunakan F# 6, kode ini dapat ditulis ulang sebagai berikut.
let readFilesTask (path1, path2) =
task {
let! bytes1 = File.ReadAllBytesAsync(path1)
let! bytes2 = File.ReadAllBytesAsync(path2)
return Array.append bytes1 bytes2
}
Dukungan tugas tersedia untuk F# 5 melalui pustaka TaskBuilder.fs dan Ply yang sangat baik. Ini harus mudah untuk memigrasikan kode ke dukungan bawaan. Namun, ada beberapa perbedaan: namespace dan inferensi jenis sedikit berbeda antara dukungan bawaan dan pustaka ini, dan beberapa anotasi jenis tambahan mungkin diperlukan. Jika perlu, Anda masih dapat menggunakan pustaka komunitas ini dengan F# 6 jika Anda mereferensikannya secara eksplisit dan membuka namespace yang benar di setiap file.
Penggunaan task {…} sangat mirip dengan menggunakan async {…}. Menggunakan task {…} memiliki beberapa keunggulan dibandingkan async {…}:
- Overhead
task {...}lebih rendah, mungkin meningkatkan performa di jalur kode panas di mana pekerjaan asinkron dijalankan dengan cepat. - Penelusuran dan langkah dalam proses debugging serta penelusuran tumpukan untuk
task {…}lebih baik. - Mengoperasikan dengan paket .NET yang mengharapkan atau menghasilkan tugas lebih mudah.
Jika Anda terbiasa dengan async {…}, ada beberapa perbedaan yang perlu diperhatikan:
-
task {…}segera menjalankan tugas hingga titik tunggu pertama. -
task {…}tidak menyebarkan token pembatalan secara implisit. -
task {…}tidak melakukan pengecekan pembatalan secara implisit. -
task {…}tidak mendukung pemanggilan ekor asinkron. Ini berarti menggunakanreturn! ..secara rekursif dapat mengakibatkan luapan tumpukan jika tidak ada jeda tunggu asinkron.
Secara umum, Anda harus mempertimbangkan untuk menggunakan task {…} daripada async {…} dalam kode baru jika Anda berinteraksi dengan pustaka .NET yang menggunakan task, dan jika Anda tidak mengandalkan tail call dari kode asinkron atau propagasi token pembatalan implisit. Dalam kode yang ada, Anda hanya boleh beralih ke task {…} setelah meninjau kode Anda untuk memastikan Anda tidak mengandalkan karakteristik yang disebutkan sebelumnya dari async {…}.
Fitur ini mengimplementasikan F# RFC FS-1097.
Sintaks pengindeksan yang lebih sederhana dengan expr[idx]
F# 6 memungkinkan sintaks expr[idx] untuk mengindeks dan mengiris koleksi.
Hingga dan termasuk F# 5, F# telah menggunakan expr.[idx] sebagai sintaks pengindeksan. Memungkinkan penggunaan expr[idx] didasarkan pada masukan yang berulang kali diterima dari orang yang mempelajari F# atau melihat F# untuk pertama kali bahwa penggunaan pengindeksan notasi titik terkesan sebagai penyimpangan yang tidak perlu dari praktik standar industri.
Ini bukan perubahan yang melanggar karena secara default, tidak ada peringatan yang dipancarkan pada penggunaan expr.[idx]. Namun, beberapa pesan informasi yang menyarankan klarifikasi kode dipancarkan. Anda juga dapat mengaktifkan pesan informasi lebih lanjut secara opsional. Misalnya, Anda dapat mengaktifkan peringatan informasi opsional (/warnon:3366) untuk mulai melaporkan penggunaan expr.[idx] notasi. Untuk informasi selengkapnya, lihat Notasi Pengindeks.
Dalam kode baru, kami merekomendasikan penggunaan expr[idx] sistematis sebagai sintaks pengindeksan.
Fitur ini mengimplementasikan F# RFC FS-1110.
Representasi struktur untuk pola aktif parsial
F# 6 menambah fitur "pola aktif" dengan representasi struktur opsional untuk pola aktif parsial. Ini memungkinkan Anda menggunakan atribut untuk membatasi pola aktif parsial untuk mengembalikan opsi nilai:
[<return: Struct>]
let (|Int|_|) str =
match System.Int32.TryParse(str) with
| true, int -> ValueSome(int)
| _ -> ValueNone
Penggunaan atribut diperlukan. Di situs penggunaan, kode tidak berubah. Hasil bersih adalah bahwa alokasi berkurang.
Fitur ini mengimplementasikan F# RFC FS-1039.
Operasi kustom yang kelebihan beban dalam ekspresi komputasi
F# 6 memungkinkan Anda menggunakan CustomOperationAttribute pada metode yang kelebihan beban.
Pertimbangkan penggunaan penyusun contentekspresi komputasi berikut:
let mem = new System.IO.MemoryStream("Stream"B)
let content = ContentBuilder()
let ceResult =
content {
body "Name"
body (ArraySegment<_>("Email"B, 0, 5))
body "Password"B 2 4
body "BYTES"B
body mem
body "Description" "of" "content"
}
body Di sini operasi kustom mengambil sejumlah argumen yang berbeda dari berbagai jenis. Ini didukung oleh implementasi penyusun berikut, yang menggunakan kelebihan beban:
type Content = ArraySegment<byte> list
type ContentBuilder() =
member _.Run(c: Content) =
let crlf = "\r\n"B
[|for part in List.rev c do
yield! part.Array[part.Offset..(part.Count+part.Offset-1)]
yield! crlf |]
member _.Yield(_) = []
[<CustomOperation("body")>]
member _.Body(c: Content, segment: ArraySegment<byte>) =
segment::c
[<CustomOperation("body")>]
member _.Body(c: Content, bytes: byte[]) =
ArraySegment<byte>(bytes, 0, bytes.Length)::c
[<CustomOperation("body")>]
member _.Body(c: Content, bytes: byte[], offset, count) =
ArraySegment<byte>(bytes, offset, count)::c
[<CustomOperation("body")>]
member _.Body(c: Content, content: System.IO.Stream) =
let mem = new System.IO.MemoryStream()
content.CopyTo(mem)
let bytes = mem.ToArray()
ArraySegment<byte>(bytes, 0, bytes.Length)::c
[<CustomOperation("body")>]
member _.Body(c: Content, [<ParamArray>] contents: string[]) =
List.rev [for c in contents -> let b = Text.Encoding.ASCII.GetBytes c in ArraySegment<_>(b,0,b.Length)] @ c
Fitur ini mengimplementasikan F# RFC FS-1056.
Pola "sebagai"
Di F# 6, sisi as kanan pola sekarang bisa menjadi pola. Ini penting ketika uji tipe telah memberikan tipe yang lebih kuat untuk input. Misalnya, pertimbangkan kode berikut:
type Pair = Pair of int * int
let analyzeObject (input: obj) =
match input with
| :? (int * int) as (x, y) -> printfn $"A tuple: {x}, {y}"
| :? Pair as Pair (x, y) -> printfn $"A DU: {x}, {y}"
| _ -> printfn "Nope"
let input = box (1, 2)
Dalam setiap kasus pola, objek input diuji berdasarkan tipe. Pada pola as, sisi kanan kini dapat berupa pola lanjutan, yang dapat mencocokkan objek dengan tipe yang lebih kuat.
Fitur ini mengimplementasikan F# RFC FS-1105.
Revisi sintaks indentasi
F# 6 menghapus sejumlah inkonsistensi dan batasan dalam penggunaan sintaks yang sadar indentasi. Lihat RFC FS-1108. Ini menyelesaikan 10 masalah signifikan yang disorot oleh pengguna F# sejak F# 4.0.
Misalnya, di F# 5 kode berikut diizinkan:
let c = (
printfn "aaaa"
printfn "bbbb"
)
Namun, kode berikut tidak diizinkan (menghasilkan peringatan):
let c = [
1
2
]
Di F# 6, keduanya diizinkan. Ini membuat F# lebih sederhana dan lebih mudah dipelajari. Kontributor komunitas F# Hadrian Tang telah memimpin hal ini, termasuk pengujian fitur sistematis yang luar biasa dan sangat berharga.
Fitur ini mengimplementasikan F# RFC FS-1108.
Konversi implisit tambahan
Di F# 6, kami telah mengaktifkan dukungan untuk konversi "implisit" dan "type-directed" tambahan, seperti yang dijelaskan dalam RFC FS-1093.
Perubahan ini membawa tiga keuntungan:
- Diperlukan lebih sedikit upcast eksplisit
- Diperlukan lebih sedikit konversi bilangan bulat eksplisit
- Dukungan kelas satu untuk konversi implisit gaya .NET ditambahkan
Fitur ini mengimplementasikan F# RFC FS-1093.
Konversi upcast implisit tambahan
F# 6 menerapkan beberapa konversi upcast implisit tambahan. Misalnya, dalam F# 5 dan versi-versi sebelumnya, upcasting diperlukan untuk ekspresi pengembalian saat mengimplementasikan fungsi di mana ekspresi memiliki subjenis yang berbeda pada cabang yang berbeda, meskipun anotasi tipe sudah diberikan. Pertimbangkan kode F# 5 berikut:
open System
open System.IO
let findInputSource () : TextReader =
if DateTime.Now.DayOfWeek = DayOfWeek.Monday then
// On Monday a TextReader
Console.In
else
// On other days a StreamReader
File.OpenText("path.txt") :> TextReader
Di sini cabang dari perhitungan bersyarat mengolah TextReader dan StreamReader masing-masing, dan upcast ditambahkan untuk membuat kedua cabang memiliki jenis StreamReader. Di F# 6, upcast ini sekarang ditambahkan secara otomatis. Ini berarti kode lebih sederhana:
let findInputSource () : TextReader =
if DateTime.Now.DayOfWeek = DayOfWeek.Monday then
// On Monday a TextReader
Console.In
else
// On other days a StreamReader
File.OpenText("path.txt")
Anda dapat secara opsional mengaktifkan peringatan /warnon:3388 untuk menampilkan peringatan setiap kali upcast implisit tambahan digunakan, seperti yang dijelaskan dalam Peringatan opsional untuk konversi implisit.
Konversi bilangan bulat implisit
Dalam F# 6, bilangan bulat 32-bit diperlebar menjadi bilangan bulat 64-bit ketika kedua jenis diketahui. Misalnya, pertimbangkan bentuk API umum:
type Tensor(…) =
static member Create(sizes: seq<int64>) = Tensor(…)
Dalam F# 5, literal bilangan bulat untuk int64 harus digunakan:
Tensor.Create([100L; 10L; 10L])
or
Tensor.Create([int64 100; int64 10; int64 10])
Di F# 6, pelebaran terjadi secara otomatis untuk int32 ke int64, int32 ke nativeint, dan int32 ke double, ketika tipe sumber dan tipe tujuan diketahui selama inferensi tipe. Jadi dalam kasus seperti contoh sebelumnya, int32 literal dapat digunakan:
Tensor.Create([100; 10; 10])
Terlepas dari perubahan ini, F# masih menggunakan perluasan eksplisit tipe numerik dalam kebanyakan kasus. Misalnya, perluasan implisit tidak berlaku untuk tipe data numerik lain, seperti int8 atau int16, atau dari float32 ke float64, atau ketika jenis sumber atau tujuan tidak diketahui. Anda juga dapat secara opsional mengaktifkan peringatan /warnon:3389 untuk menampilkan peringatan di setiap titik pellebaran numerik implisit digunakan, seperti yang dijelaskan dalam Peringatan opsional untuk konversi implisit.
Dukungan kelas utama untuk konversi implisit gaya .NET
Di F# 6, konversi .NET "op_Implicit" diterapkan secara otomatis dalam kode F# saat memanggil metode. Misalnya, di F# 5 perlu digunakan XName.op_Implicit saat bekerja dengan API .NET untuk XML:
open System.Xml.Linq
let purchaseOrder = XElement.Load("PurchaseOrder.xml")
let partNos = purchaseOrder.Descendants(XName.op_Implicit "Item")
Di F# 6, op_Implicit konversi diterapkan secara otomatis untuk ekspresi argumen ketika tipe tersedia baik untuk ekspresi sumber maupun tipe target.
open System.Xml.Linq
let purchaseOrder = XElement.Load("PurchaseOrder.xml")
let partNos = purchaseOrder.Descendants("Item")
Anda dapat opsional mengaktifkan peringatan /warnon:3395 untuk menampilkan peringatan di setiap titik di mana pelebaran konversi digunakan pada argumen metode, seperti yang dijelaskan dalam Peringatan opsional untuk konversi implisit.
Nota
Dalam rilis pertama F# 6, nomor peringatan ini adalah /warnon:3390. Karena konflik, nomor peringatan kemudian diperbarui ke /warnon:3395.
Peringatan opsional untuk konversi implisit
Konversi terarah jenis dan implisit dapat berinteraksi dengan buruk dengan inferensi jenis dan menyebabkan kode yang lebih sulit dipahami. Untuk alasan ini, beberapa mitigasi ada untuk membantu memastikan fitur ini tidak disalahgunakan dalam kode F#. Pertama, jenis sumber dan tujuan harus sangat diketahui, tanpa ambiguitas atau inferensi jenis tambahan yang timbul. Kedua, peringatan keikutsertaan dapat diaktifkan untuk melaporkan penggunaan konversi implisit, dengan satu peringatan aktif secara default:
-
/warnon:3388(peningkatan implisit tambahan) -
/warnon:3389(pelebaran numerik implisit) -
/warnon:3391(op_Implicit pada argumen non-metode, aktif secara default) -
/warnon:3395(op_Implicit pada parameter metode)
Jika tim Anda ingin melarang semua penggunaan konversi implisit, Anda juga dapat menentukan /warnaserror:3388, , /warnaserror:3389/warnaserror:3391, dan /warnaserror:3395.
Pemformatan untuk angka biner
F# 6 menambahkan %B pola ke penentu format yang tersedia untuk format angka biner. Pertimbangkan kode F# berikut:
printf "%o" 123
printf "%B" 123
Kode ini mencetak output berikut:
173
1111011
Fitur ini mengimplementasikan F# RFC FS-1100.
Penghapusan pengikatan saat penggunaan
F# 6 memungkinkan _ untuk digunakan dalam pengikatan use , misalnya:
let doSomething () =
use _ = System.IO.File.OpenText("input.txt")
printfn "reading the file"
Fitur ini mengimplementasikan F# RFC FS-1102.
InlineIfLambda
Pengkompilasi F# mencakup pengoptimal yang melakukan inlining kode. Di F# 6, kami telah menambahkan fitur deklaratif baru yang memungkinkan kode untuk secara opsional mengindikasikan bahwa, jika argumen ditentukan sebagai fungsi lambda, maka argumen tersebut harus selalu di-inline pada lokasi pemanggilan.
Misalnya, pertimbangkan fungsi berikut iterateTwice untuk melintasi array:
let inline iterateTwice ([<InlineIfLambda>] action) (array: 'T[]) =
for j = 0 to array.Length-1 do
action array[j]
for j = 0 to array.Length-1 do
action array[j]
Jika situs panggilan adalah:
let arr = [| 1.. 100 |]
let mutable sum = 0
arr |> iterateTwice (fun x ->
sum <- sum + x)
Kemudian setelah inlining dan pengoptimalan lainnya, kode menjadi:
let arr = [| 1.. 100 |]
let mutable sum = 0
for j = 0 to arr.Length-1 do
sum <- sum + arr[j]
for j = 0 to arr.Length-1 do
sum <- sum + arr[j]
Tidak seperti versi F#sebelumnya, pengoptimalan ini diterapkan terlepas dari ukuran ekspresi lambda yang terlibat. Fitur ini juga dapat digunakan untuk mengimplementasikan unrolling loop dan transformasi serupa dengan lebih andal.
Peringatan opsi ikut serta (/warnon:3517, secara default dinonaktifkan) dapat diaktifkan untuk menunjukkan tempat dalam kode Anda di mana InlineIfLambda argumen tidak terikat ke ekspresi lambda di lokasi pemanggilan. Dalam situasi normal, peringatan ini tidak boleh diaktifkan. Namun, dalam jenis pemrograman berkinerja tinggi tertentu, dapat berguna untuk memastikan semua kode sebaris dan diratakan.
Fitur ini mengimplementasikan F# RFC FS-1098.
Kode yang dapat diulang
task {…} Dukungan F# 6 dibangun di atas fondasi yang disebut kode yang dapat dilanjutkanRFC FS-1087. Kode yang dapat diulang adalah fitur teknis yang dapat digunakan untuk membangun banyak jenis mesin status asinkron dan menghasilkan performa tinggi.
Fungsi koleksi tambahan
FSharp.Core 6.0.0 menambahkan lima operasi baru ke fungsi pengumpulan inti. Fungsi-fungsi ini adalah:
- List/Array/Seq.insertAt
- List/Array/Seq.removeAt
- List/Array/Seq.updateAt
- List/Array/Seq.insertManyAt
- List/Array/Seq.removeManyAt
Semua fungsi ini melakukan operasi salin dan perbarui pada jenis atau urutan koleksi yang sesuai. Jenis operasi ini adalah bentuk dari "pembaruan fungsi". Untuk contoh penggunaan fungsi ini, lihat dokumentasi yang sesuai, misalnya, List.insertAt.
Sebagai contoh, pertimbangkan model, pesan, dan logika pembaruan untuk aplikasi "Daftar Todo" sederhana yang ditulis dalam gaya Elmish. Di sini pengguna berinteraksi dengan aplikasi, menghasilkan pesan, dan update fungsi memproses pesan-pesan ini, menghasilkan model baru:
type Model =
{ ToDo: string list }
type Message =
| InsertToDo of index: int * what: string
| RemoveToDo of index: int
| LoadedToDos of index: int * what: string list
let update (model: Model) (message: Message) =
match message with
| InsertToDo (index, what) ->
{ model with ToDo = model.ToDo |> List.insertAt index what }
| RemoveToDo index ->
{ model with ToDo = model.ToDo |> List.removeAt index }
| LoadedToDos (index, what) ->
{ model with ToDo = model.ToDo |> List.insertManyAt index what }
Dengan fungsi-fungsi baru ini, logikanya jelas dan sederhana dan hanya bergantung pada data yang tidak dapat diubah.
Fitur ini mengimplementasikan F# RFC FS-1113.
Peta memiliki Kunci dan Nilai
Di FSharp.Core 6.0.0, Map jenis sekarang mendukung properti Kunci dan Nilai . Properti ini tidak menyalin koleksi yang mendasar.
Fitur ini didokumenkan dalam F# RFC FS-1113.
Intrinsik tambahan untuk NativePtr
FSharp.Core 6.0.0 menambahkan intrinsik baru ke modul NativePtr :
NativePtr.nullPtrNativePtr.isNullPtrNativePtr.initBlockNativePtr.clearNativePtr.copyNativePtr.copyBlockNativePtr.ofILSigPtrNativePtr.toILSigPtr
Seperti halnya fungsi lain dalam NativePtr, fungsi-fungsi ini sebaris, dan penggunaannya memancarkan peringatan kecuali /nowarn:9 digunakan. Penggunaan fungsi-fungsi ini dibatasi untuk jenis yang tidak dikelola.
Fitur ini didokumenkan dalam F# RFC FS-1109.
Jenis numerik tambahan dengan anotasi unit
Dalam F# 6, tipe atau alias singkatan tipe berikut sekarang mendukung anotasi satuan pengukuran. Penambahan baru ditampilkan dalam huruf tebal:
| Alias F# | Jenis CLR |
|---|---|
float32/single |
System.Single |
float/double |
System.Double |
decimal |
System.Decimal |
sbyte/int8 |
System.SByte |
int16 |
System.Int16 |
int/int32 |
System.Int32 |
int64 |
System.Int64 |
byte/uint8 |
System.Byte |
uint16 |
System.UInt16 |
uint/uint32 |
System.UInt32 |
uint64 |
System.UIn64 |
nativeint |
System.IntPtr |
unativeint |
System.UIntPtr |
Misalnya, Anda dapat membuat anotasi bilangan bulat yang tidak ditandatangani sebagai berikut:
[<Measure>]
type days
let better_age = 3u<days>
Fitur ini didokumenkan dalam F# RFC FS-1091.
Peringatan informatif untuk operator simbolis yang jarang digunakan
F# 6 menambahkan panduan lunak yang mendenormalisasi penggunaan :=, , !incr, dan decr di F# 6 dan seterusnya. Menggunakan operator dan fungsi ini menghasilkan pesan informasi yang meminta Anda untuk mengganti kode Anda dengan penggunaan Value properti secara eksplisit.
Dalam pemrograman F#, sel referensi dapat digunakan untuk register yang dapat diubah dan dialokasikan di heap. Meskipun kadang-kadang berguna, mereka jarang diperlukan dalam pengkodan F# modern, karena let mutable dapat digunakan sebagai gantinya. Pustaka inti F# mencakup dua operator := dan ! dua fungsi incr dan decr khususnya terkait dengan panggilan referensi. Kehadiran operator ini membuat sel referensi lebih terpusat pada pemrograman F# daripada yang diperlukan, mengharuskan semua pemrogram F# untuk mengetahui operator ini. Selanjutnya, operator ! dapat dengan mudah dikacaukan dengan operasi not dalam C# dan bahasa lain, yang bisa menjadi sumber bug yang sulit dideteksi saat menerjemahkan kode.
Alasan perubahan ini adalah untuk mengurangi jumlah operator yang perlu diketahui programmer F#, dan dengan demikian menyederhanakan F# untuk pemula.
Misalnya, pertimbangkan kode F# 5 berikut:
let r = ref 0
let doSomething() =
printfn "doing something"
r := !r + 1
Pertama, sel referensi jarang diperlukan dalam pengkodan F# modern, seperti let mutable biasanya dapat digunakan sebagai gantinya:
let mutable r = 0
let doSomething() =
printfn "doing something"
r <- r + 1
Jika Anda menggunakan sel referensi, F# 6 memancarkan peringatan informasi yang meminta Anda untuk mengubah baris terakhir menjadi r.Value <- r.Value + 1, dan menautkan Anda ke panduan lebih lanjut tentang penggunaan sel referensi yang sesuai.
let r = ref 0
let doSomething() =
printfn "doing something"
r.Value <- r.Value + 1
Pesan-pesan ini bukan peringatan; mereka adalah "pesan informasi" yang ditampilkan dalam IDE dan output kompilator. F# tetap kompatibel dengan versi sebelumnya.
Fitur ini mengimplementasikan F# RFC FS-1111.
Alat F#: .NET 6 default untuk pembuatan skrip di Visual Studio
Jika Anda membuka atau menjalankan Skrip F# (.fsx) di Visual Studio, secara default skrip akan dianalisis dan dijalankan menggunakan .NET 6 dengan eksekusi 64-bit. Fungsionalitas ini tersedia dalam pratinjau pada rilis terbaru Visual Studio 2019 dan sekarang diaktifkan secara bawaan.
Untuk mengaktifkan pembuatan skrip .NET Framework, pilihOpsi>Alat>F# Alat>F# Interaktif. Atur Gunakan .NET Core Scripting ke false, lalu mulai ulang jendela Interaktif F#. Pengaturan ini memengaruhi pengeditan skrip dan eksekusi skrip. Untuk mengaktifkan eksekusi 32-bit untuk skrip .NET Framework, atur juga F# Interaktif 64-bit ke false. Tidak ada opsi 32-bit untuk skrip .NET Core.
Alat F#: Sematkan versi SDK skrip F# Anda
Jika Anda menjalankan skrip menggunakan dotnet fsi di direktori yang berisi file global.json dengan pengaturan .NET SDK, maka versi .NET SDK yang tercantum akan digunakan untuk mengeksekusi dan mengedit skrip. Fitur ini telah tersedia di versi F# 5 yang lebih baru.
Misalnya, asumsikan ada skrip di direktori dengan file global.json berikut yang menentukan kebijakan versi .NET SDK:
{
"sdk": {
"version": "5.0.200",
"rollForward": "minor"
}
}
Jika Anda sekarang menjalankan skrip menggunakan dotnet fsi, dari direktori ini, versi SDK akan dipatuhi. Ini adalah fitur canggih yang memungkinkan Anda "mengunci" SDK yang digunakan untuk mengkompilasi, menganalisis, dan menjalankan skrip Anda.
Jika Anda membuka dan mengedit skrip di Visual Studio dan IDE lainnya, tools akan mematuhi pengaturan ini saat menganalisis dan memeriksa skrip Anda. Jika SDK tidak ditemukan, Anda harus menginstalnya di komputer pengembangan Anda.
Di Linux dan sistem Unix lainnya, Anda dapat menggabungkan ini dengan shebang untuk juga menentukan versi bahasa untuk eksekusi langsung skrip. Shebang sederhana untuk script.fsx adalah:
#!/usr/bin/env -S dotnet fsi
printfn "Hello, world"
Sekarang skrip dapat dieksekusi langsung dengan script.fsx. Anda dapat menggabungkan ini dengan versi bahasa tertentu yang tidak default seperti ini:
#!/usr/bin/env -S dotnet fsi --langversion:5.0
Nota
Pengaturan ini diabaikan oleh alat pengeditan, yang akan menganalisis skrip dengan menggunakan versi bahasa terbaru.
Menghapus fitur warisan
Sejak F# 2.0, beberapa fitur warisan yang tidak digunakan lagi telah lama memberikan peringatan. Menggunakan fitur-fitur ini di F# 6 memberikan kesalahan kecuali Anda secara eksplisit menggunakan /langversion:5.0. Fitur yang memberikan kesalahan adalah:
- Beberapa parameter generik menggunakan nama jenis postfix, misalnya
(int, int) Dictionary. Ini menjadi kesalahan dalam F# 6. SintaksDictionary<int,int>standar harus digunakan sebagai gantinya. -
#indent "off". Ini menjadi kesalahan. -
x.(expr). Ini menjadi kesalahan. -
module M = struct … end. Ini menjadi kesalahan. - Penggunaan input
*.mldan*.mli. Ini menjadi kesalahan. - Penggunaan
(*IF-CAML*)atau(*IF-OCAML*). Ini menjadi kesalahan. - Penggunaan
land,lor,lxor,lsl,lsr, atauasrsebagai operator infix. Ini adalah kata kunci infiks di F# karena memang merupakan kata kunci infiks di OCaml dan tidak terdefinisi dalam FSharp.Core. Menggunakan kata kunci ini sekarang akan memancarkan peringatan.
Ini mengimplementasikan F# RFC FS-1114.