Hangi alanlarda F # kullanımı C # 'dan daha uygun olabilir? [kapalı]


210

Son birkaç yıl içinde F #, Microsoft'un OCaml, ML ve Haskell'de kuluçkalanmış birçok fikri kullanarak tam olarak desteklenen dillerden birine dönüştü.

Son birkaç yıldır C #, daha fazla işlevsel dil özelliği sunarak genel amaçlı özelliklerini genişletti: LINQ (liste anlama), Lambdas, Kapanışlar, Anonim Delegeler ve daha fazlası ...

C # 'ın bu işlevsel özellikleri benimsemesi ve F #' ın taksimsiz bir işlevsel dil olarak sınıflandırılması göz önüne alındığında (istediğinizde bir işlev çağrıldığında çerçeve kitaplıklarına erişmenizi veya paylaşılan durumu değiştirmenizi sağlar), her birinin dili olmasına rağmen iki dil arasında güçlü bir benzerlik vardır kendi kutupsal karşıt birincil vurgusu.

Üretim çok dilli programlarınızda bu iki dili kullanan başarılı modellerle ve geçen yıl içinde F # ile yazdığınız üretim yazılımı (web uygulamaları, istemci uygulamaları, sunucu uygulamaları) ile ilgili alanlarla ilgileniyorum. C # ile yazılmış.

Yanıtlar:


258

Bir enerji santrali portföyü için ulusal enerji üretim programını bir enerji şirketi için bir ticaret pozisyonuna dengelemek için bir uygulama yazdım. Istemci ve sunucu bileşenleri C # vardı ama hesaplama motoru F # yazılmıştır.

Bu uygulamanın kalbindeki karmaşıklığı gidermek için F # kullanımı, kurumsal yazılım içindeki dil için tatlı bir nokta, yani büyük veri kümelerinin algoritmik olarak karmaşık analizi açıkça göstermektedir. Deneyimlerim çok olumlu oldu. Özellikle:

Ölçü birimleri Çalıştığım endüstri birimlerle doludur. Uyguladığım denklemler (genellikle geometrik nitelikte) zaman, güç ve enerji birimleriyle ilgiliydi. Tip sisteminin, fonksiyonların giriş ve çıkış birimlerinin doğruluğunu doğrulaması, hem test etme hem de kodu okuma / anlama açısından büyük bir zaman tasarrufu sağlar. Önceki sistemlerin eğilimli olduğu bütün bir hata sınıfını ortadan kaldırır.

Keşifsel programlama Betik dosyalarıyla ve REPL (F # Interactive) ile çalışmak, bir uygulamaya başlamadan önce, daha geleneksel düzenleme / derleme / çalıştırma / test döngüsüne göre çözüm alanını daha etkili bir şekilde keşfetmeme izin verdi. Bir programcının problem ve oyundaki tasarım gerilimleri hakkındaki anlayışlarını geliştirmesi çok doğal bir yoldur.

Birim testi Yan etkisi olmayan fonksiyonlar ve değiştirilemez veri yapıları kullanılarak yazılan kodlar test etmek keyiflidir. İşleri bertaraf etmek için karmaşık zamana bağlı etkileşimler ya da alay edilecek büyük bağımlılık grupları yoktur.

Birlikte çalışma C # 'da hesaplama motorunun arayüzünü tanımladım ve F #' da hesaplamayı uyguladım. Daha sonra hesaplama motoru, birlikte çalışabilirlikle ilgili herhangi bir endişe duymadan kullanması gereken herhangi bir C # modülüne enjekte edilebilir. Sorunsuz. C # programcısı asla bilmenize gerek yok.

Kod azaltma Hesaplama motoruna beslenen verilerin çoğu vektörler ve matrisler şeklindeydi. Daha üst düzey fonksiyonlar, bunları minimum yaygara, minimum kod ile kahvaltıda yerler. Güzel.

Hataların olmaması Fonksiyonel programlama garip gelebilir. Ben bir tür denetleyicisi geçmek kod çalışmasını geçmek için çalışıyoruz çalışıyoruz ama tip denetleyicisi thats memnun kez, o çalışır. Neredeyse ikili, derlenmeyecek ya da doğru olacak. Tuhaf kenar durumu hataları en aza indirilir, özyineleme ve daha yüksek dereceli işlevler, kenar durumu hatalarını tanıtan birçok kitap tutma kodunu kaldırır.

Paralellik Sonuçta ortaya çıkan uygulamanın fonksiyonel saflığı, veri vektörlerinin işlenmesinde içsel paralellikten faydalanmak için olgunlaştırır. Belki de şimdi .NET 4 dışarı şimdi gideceğim yerdir.


18
F # 'ın sayı sıkıcı motorlar için neden çok uygun olduğunu açıklayan +1. Ölçü birimlerinden bahsetmek için başka bir (sanal) +1. Dilin bu kısmı daha sık bahsedilmeyi hak ediyor.
cfern

5
Büyük cevap, ilgili, çağdaş ve karmaşıklık ile başa çıkmak için F # uygunluğunu özetliyor, onu okumaktan çok şey öğrendim, teşekkürler
Peter McG

Simon'a ve Don'un dün gece söylediği gibi büyük cevap, son slaytlarında alıntı yaptı. "Sepete ekle" bağlantısı ekleme zamanı geldi mi?
Chris Ballard

1
merhaba, bize uygulama mimariniz hakkında daha fazla bilgi verebilir misiniz?
Nikos

76

Microsoft Research'teki stajım sırasında Visual Studio IntelliSense for F # (kendisi F # ile yazılmış) üzerinde çalıştım. Zaten önceki C # projelerinden IntelliSense ile biraz deneyimim vardı, bu yüzden ikisini karşılaştırabileceğimi düşünüyorum.

  • Visual Studio Genişletilebilirliği hala COM dayanmaktadır, bu nedenle çok güzel .NET nesneleri olmayan nesnelerle uğraşmanız gerekir (ve kesinlikle işlevsel değildir), ancak C # ve F # arasında büyük bir fark olduğunu hissetmiyorum (sorunsuz çalışır) F # 'den)

  • F # 'da program kodunu temsil etmek için kullanılan veri yapıları çoğunlukla ayrımcı birliklerdir (bunlar C #' da makul bir şekilde desteklenmez) ve bu tür bir uygulama için büyük bir fark yaratır (program kodu gibi ağaç yapılarını işlemeniz gereken yerlerde) ). Ayrımlanmış sendikalar ve kalıp eşleme, kodu daha iyi yapılandırmanıza olanak tanır (ilgili yöntemleri sanal yöntemlerde kullanmak yerine tek bir yerde saklamanızı sağlar)

Daha önce, F # için CodeDOM sağlayıcısı üzerinde de çalıştım (ayrıca F # ile yazılmış). Aslında C # ilk deneyler yaptım, ama daha sonra kodu F # dönüştürdü.

  • CodeDOM sağlayıcısı, .NET nesneleri kullanılarak temsil edilen bazı yapıları geçmelidir, bu nedenle kendi veri gösterimlerinizi icat etmek için çok fazla alan yoktur (F #'ın güzel faydalar sağlayabileceği alandır).

  • Ancak, görevi kolaylaştıran birçok küçük F # özelliği vardı. Bir dize üretmeniz gerektiğinden, dize oluşturmak (kullanarak StringBuilder) için özel işleçler tanımladım ve bunları ve daha üst düzey işlevleri (örneğin, belirtilen dize kullanılarak ayrılmış nesnelerin listesini biçimlendirmek için) kullanarak kodu uyguladım. tekrarlama (ve sıkıcı foreachdöngüler).

Bunlar nispeten spesifik iki örnektir, ancak her ikisi de programların veya ifadelerin temsili veya daha genel olarak karmaşık ağaç benzeri veri yapıları ile çalışmakla ilgilidir. Bu alanda F # kesinlikle iyi bir seçim olduğunu düşünüyorum (C # fonksiyonel özellikleri ne olursa olsun).


6
Microsoft içinde F # alımının kesinlikle yüksek olduğuna dair çok ilginç, daha fazla kanıt, ne büyük bir staj olmalı!
Peter McG

43

Dünyanın ilk ticari ürününü F # ( Görselleştirme için F # ) ve ikincisi ( Sayısallar için F # ) ile F # ( The F # .NET Journal ) hakkındaki ilk ticari literatürü gönderdik ve mevcut sürümle ilgili tek kitabı yazıp yayınladık of F # ( Teknik Hesaplama için Görsel F # 2010 ).

C # ile yazılmış benzer satırlar boyunca ürünler gönderiyoruz (örneğin, bu ) ama aynı zamanda OCaml'ın ticari kullanımında güçlü bir arka planımız vardı. 2006'da hala bir araştırma prototipi iken F # 'in hevesli erken benimseyenleriydi, çünkü endüstriyel güçte .NET platformunda iyi bir modern OCaml benzeri dile sahip olma potansiyelini anladık ve sonuç olarak onu üretmeye zorladık. Sonuç inanılmaz bir başarı oldu ve F #, yüce beklentilerimizi çok aştı.

Bizim için F #'ın birçok farklı avantajı var ve bunu çok çeşitli uygulamalar için kullanıyoruz. Üretimde yüz binlerce satır F # kodu var. Artık tüm LOB uygulamalarımız için F # kullanıyoruz : kredi kartı işlemlerimiz F # kodu kullanılarak işleniyor, ürün bildirimlerimiz F # kodu kullanılarak gönderiliyor, aboneliklerimiz F # kodu kullanılarak işleniyor, hesaplarımız F # kodu vb. Belki de burada temettü ödeyen ana dil özelliği kalıp eşleştirme. Hatta son sözümüzü vurgulamak için F # renk sözdizimini kullandık ...

Görselleştirme kitaplığımız büyük bir satıcıdır ve işlevselliği Visual Studio'da çalışan F # interaktif merkezindedir. Kütüphanemiz, etkileşimli 2D ve 3D görselleştirmeleri minimum çaba ile üretme yeteneği ile bunu artırır (örn.Plot([Function sin], (-6., 6.))sinüs dalgası çizmek için). Özellikle, tüm iş parçacığı sorunları tamamen otomatiktir, böylece kullanıcılar UI iş parçacıkları ve dağıtım konusunda endişelenmek zorunda kalmazlar. Birinci sınıf fonksiyonlar ve tembellik, kütüphanenin bu kısmını yazarken son derece değerliydi ve cebirsel veri tipleri başka yerlerde yaygın olarak kullanılıyordu. Tahmin edilebilir performans, müşterilerimiz WPF'nin hit testinde performans hatalarına çarptığında ve 10.000 × performans artışı için ilgili kodu F # 'da kolayca uygulayabildiklerinde de değerli olduğunu kanıtladı. Bu ürünün GUI'sinin serbest biçimli yapısı nedeniyle, GUI tasarımcısı ve C # yararlı olmazdı.

Çalışmalarımızın çoğu, hem ticari kütüphanelerimiz hem de kitaplarımız dahil olmak üzere sayısal yöntemler etrafında dönmektedir. F #, bu alanda C # 'dan çok daha güçlüdür, çünkü asgari performans cezaları ile üst düzey soyutlamalar (örn. Üst düzey işlevler) sunar. Bu bağlamda en ilgi çekici sonucumuz, LAPACK'in referans uygulamasından Fortran kodundan 20 × daha kısa, satıcı tarafından ayarlanmış Intel Math'dan 3 kat daha hızlı olan doğrusal cebirden QR ayrışmasının basit ama genelleştirilmiş bir uygulamasının oluşturulmasıydı. Çekirdek Kütüphanesi ve daha genel çünkü kodumuz her türlü matris, hatta sembolik matrisleri işleyebilir!

Şu anda WPF / Silverlight bileşenlerini F # (bağırsaklar için) ve C # (şim için) karışımında geliştiriyoruz, WPF uygulamalarını yazılım ürünlerimiz için etkileşimli el kitapları görevi görecek şekilde tasarlıyoruz ve yeni bir kitap olan Multicore F # yazıyorum. .NET üzerinde paylaşılan bellek paralel programlama için kesin bir kılavuz olacaktır.


"Bilim adamları için F #" yazan Jon Harrop siz misiniz?
Andre Artus

7
Evet. 5 yıl önce Bilim Adamları için F # yazdım.
Jon Harrop

Sondan bir önceki paragrafta bahsettiğiniz F # 'daki QR ayrıştırma kodu için bazı tür referanslarınız var mı? Teşekkürler.
Samik R

@SamikR: Hayır, üzgünüm. Ticari kod budur. Yine de yazmak kolaydı.
Jon Harrop

@ Multicore F # ile ilgili herhangi bir kelime söylediniz mi?
profesör bigglesworth

25

Son 6 aydır, Visual Studio 2010 için bir Vim öykünme katmanı üzerinde çalışıyorum. Github'da ücretsiz olarak bulunan tüm kaynaklarla birlikte ücretsiz bir ürün

Proje, farklı bir katmanı temsil eden 3 DLL'ye bölünür. Her katmanın karşılık gelen birim testi dll vardır.

  1. Vim Motoru: F #
  2. Süslemeler ve editör entegrasyonu için WPF katmanı: C #
  3. Visual Studio Entegrasyonu katmanı: C #

Bu F # ile yaptığım ilk büyük proje ve dili sevdiğimi söylemeliyim. Birçok yönden bu projeyi F # öğrenme yöntemi olarak kullandım (ve projenin geçmişine bakarsanız bu öğrenme eğrisi çok belirgindir).

F # hakkında en şaşırtıcı bulduğum şey, bir dilin ne kadar özlü olduğu. Vim motoru mantığın büyük kısmını içerir, ancak toplam kod tabanının sadece% 30'unu oluşturur.


19
Editör ... fonksiyonel dil ... vi emülasyonu ... emacs'i yeniden icat ettiniz. NOOOOOOOOOOOOOOOOOOOOOOO!
Ben Voigt

2
Dışında "Sertifikalı% 100 parantez içermez" :)
Pavel Minaev

@Pavel, elbette tuples ve .net yöntemi çağrıları hariç
JaredPar

26
Burada iki şey var. Her şeyden önce, ()F # 'da tuples gerekmez - ,operatör onları yaratan şeydir, bu yüzden let x = 1,2zaten herhangi bir paren olmadan geçerli bir tuple. İkincisi, F # içindeki herhangi bir paren çifti begin.. end(bu ML'den devralınır) çiftleri ile değiştirilebilir - bu nedenle, örneğin, "foo".IndexOf begin 'a', 1 endgeçerli bir .NET yöntemi çağrısıdır. Eğer hiç parensiz olmak istediyseniz, F # bunu yapmanıza olanak tanıyan bir dildir :)
Pavel Minaev

Komik yorum Pavel! Bunu bilmiyordum. Ben büyük gruplama bloklarla bazı durumlarda, aslında tercih olabileceğini düşünmek begin.. end. AYRICA: VsVim KURALLARI!
Dan Fitch

13

F # Visual Studio bileşenleri için çok sayıda birim testi F # ile yazılmıştır. VS'nin dışında, çeşitli Visual Studio bitleriyle alay ediyorlar. Arabirimler uygulayan anonim nesneleri gizleme yeteneği, alaycı bir çerçeve / araç yerine kullanışlıdır. Sadece yazabilirim

let owpe : string list ref = ref []
let vsOutputWindowPane = 
    { new IVsOutputWindowPane with
        member this.Activate () = err(__LINE__)
        member this.Clear () = owpe := []; 0
        member this.FlushToTaskList () = VSConstants.S_OK
        member this.GetName(pbstrPaneName) = err(__LINE__)
        member this.Hide () = err(__LINE__)
        member this.OutputString(pszOutputString) = owpe := pszOutputString :: !owpe ; 0
        member this.OutputStringThreadSafe(pszOutputString) = owpe := pszOutputString :: !owpe ; 0
        member this.OutputTaskItemString(pszOutputString, nPriority, nCategory, pszSubcategory, nBitmap, pszFilename, nLineNum, pszTaskItemText) = err(__LINE__)
        member this.OutputTaskItemStringEx(pszOutputString, nPriority, nCategory, pszSubcategory, nBitmap, pszFilename, nLineNum, pszTaskItemText, pszLookupKwd) = err(__LINE__)
        member this.SetName(pszPaneName) = err(__LINE__)
    }            
DoSomethingThatNeedsA(vsOutputWindowPane)
assert( !owpe = expectedOutputStringList )

Bir örneğin bir örneğini gerektiğinde IVsOutputWindowPanesonunda arayacaktır başka bileşene geçmesine OutputStringve Clearve sonra incelemek string list refbeklenen çıkışı yazılmıştır olmadığını görmek için testin sonunda nesne.


İlginçtir, Microsoft içinde F # alımının kesinlikle yüksek olduğuna dair daha fazla kanıt. F # 'da arayüzler uygulayan anonim nesneler oluşturabileceğinizi bilmiyordum
Peter McG

9

F # içindeki Lex-Yacc uygulamasını kullanarak özel kurallar motor dili yazdık

Yorum yanıtı eklemek için DÜZENLE

C # 'da lex / yacc uygulaması yoktu. (bildiğimiz kadarıyla ve F # biriydi)

Ayrıştırmayı kendimiz inşa etmek mümkün olurdu, ama düpedüz bir acı olurdu.

Bu konuda harici kütüphaneler gibi bazı öneriler gösterilmektedir, ancak baş mimarımız fonksiyonel dillerde eski bir eldir, bu nedenle F # kullanma seçeneği beyinsizdir.


+1 Daha önce C # ile yazmış olsaydınız, belirli bir nedenden dolayı uygunsuz mu yoksa yavaş mı?
Peter McG

@Peter McGrattan En azından yazı yazılırken (yazılım), C # 'da lex / yacc uygulaması yoktu. Ayrıştırmayı kendimiz inşa etmek mümkün olurdu, ama düpedüz bir acı olurdu. stackoverflow.com/questions/540593/lex-yacc-for-c diğer bazı önerileri gösteriyor, ancak baş mimarımız işlevsel dillerde eski bir el, bu yüzden F # kullanma seçeneği beyinsizdi
johnc

C # için hiçbir lex / yacc olmadığını düşündüyseniz, korkarım ki bunun için yeterince sert görünmüyordunuz (F # 'dan daha eski bir tane var) dedi. c # daha o çivi çekiç
Rune FS

Ben fslex / fxyacc ile kendim F # kullandım, bir "üretim" projesinde olmasa da (henüz yayınlanmadı) - VSIL için MSIL sözdizimi vurgulama ve kod tamamlama uzantısı. F # kullanmanın en büyük yararı, ayrıştırma ağaçlarını temsil etmek için çok uygun olan ADT'leri almanızdır. Ayrıca, fermuarlar kullanmak ( en.wikipedia.org/wiki/Zipper_(data_sttruc) ) artımlı lexing yapmayı kolaylaştırır - ve fonksiyonel olan fermuarlar F # 'de kısaca manipüle etmek daha kolaydır.
Pavel Minaev

7

Şu anda bir programlama dili için derleme üzerinde çalışıyorum. Derleyici tamamen F # ile yazılmıştır. Derleyici (lex ve ayrıştırıcı yapının yanı sıra lex / yacc ile birlikte) temel olarak karmaşık bir ağaç benzeri yapının dönüşümü olarak inşa edilir.

Diğerleri tarafından da belirtildiği gibi, sendikalar ve kalıp eşleştirme bu tür veri yapısı ile çalışmayı, kodun "her yerde" sanal yöntemlere dökülmesinden çok daha kolay hale getirir.

Derleyici üzerinde çalışmaya başlamadan önce herhangi bir F # çalışması yapmamıştım (bununla birlikte MoscowML adı verilen başka bir OCaml varyantında derleyiciler vardı) ve Jared'in ilk olarak hangi parçaları ilk yaptığım koddan göründüğünü belirtiyordum ama genel olarak F # kolay buldum on yıl boyunca esas olarak OO kodlandıktan sonra tekrar ayarlanan FP zihnine girmeyi öğrenmek biraz daha uzun sürecektir.

ağaçlar bir yana çalışma Ben algoritma açıklayan kod algoritması açıklayan kod sahip FP (F # dahil) ana yarar yazma yeteneği bulmak Ben algoritmahm nasıl uyguladığımı açıklayan C # aksine uygulamaya çalışıyorum .


6

Kişisel deneyim değil, ancak Microsoft folk ile F # hakkında konuştukları bir DNR bölümünü (sanırım bu ) dinleyebilirsiniz . Önemsiz olmaktan uzak Xbox Live puanlama sisteminin çoğunu F # kullanarak yazdılar. Sistem yüzlerce makine arasında büyük çapta ölçeklendi ve çok memnun kaldılar.


5

Üretimde olup olmadığını bilmiyorum, ama "Go of Path" için AI F # ile yazılmıştı:

http://research.microsoft.com/en-us/events/techvista2010/demolist.aspx#ThePathofGo

Go's Path: Xbox 360 için Microsoft Araştırma Oyunu

Bu demo, Microsoft Research Cambridge'de şirket içinde üretilen Go oyununa dayanan bir Xbox 360 oyunu sergiliyor. Go, Doğu Asya'daki en ünlü masa oyunlarından biridir, 4000 yıl önce Çin'de doğmuştur. Oyunun aldatıcı sadeliğinin arkasında büyük karmaşıklık gizleniyor. Öğrenmesi sadece birkaç dakika sürer, ancak ustalaşması bir ömür sürer. Bilgisayarlar Satranç'ta insan becerilerini aşmış olsa da, Go için rekabetçi bir AI uygulamak bir araştırma zorluğu olmaya devam ediyor. Oyun, Microsoft Research Cambridge'de geliştirilen üç teknoloji tarafından desteklenmektedir: Go, F # dili ve TrueSkill ™ 'i çevrimiçi oyuncularla eşleştirmek için oynayabilecek bir AI. AI, F # ile uygulanır ve Xbox 360'ta .net kompakt çerçevesinde verimli bir şekilde çalışma zorluğunu karşılar. Bu oyun sizi görsel olarak çarpıcı 3D sahnelere yerleştirir. XNA ortamı kullanılarak yönetilen kodda tamamen geliştirilmiştir.

(Başka biri zaten "TrueSkill" den bahsetti.)


Büyüleyici: F #, XBox üzerindeki kompakt çerçevede çalışıyor. FSharp.Core.optdata FSharp.Core.sigdata ile birlikte CF olmayan derlemeler başvurmuyor mu?
Peter McG

1
CTP, .NETCF için oluşturulan ayrı bir FSharp.Core ile birlikte gelir. (Ayrıca Silverlight için ayrı bir FSharp.Core var.)
Brian

Bahsettiğiniz bu CTP nedir?
Jwosty
Sitemizi kullandığınızda şunları okuyup anladığınızı kabul etmiş olursunuz: Çerez Politikası ve Gizlilik Politikası.
Licensed under cc by-sa 3.0 with attribution required.