Paradigma Pengaturcaraan
Paradigma pengaturcaraan ialah rangka kerja yang terdiri daripada alatan untuk memikirkan masalah dan merealisasikan visi untuk masalah tersebut. Banyak bahasa moden adalah poliparadigma (atau multi-paradigma): mereka menyokong banyak paradigma pengaturcaraan yang berbeza, seperti berorientasikan objek, pengaturcaraan meta, berfungsi, prosedur, dll.
Paradigma Pengaturcaraan Fungsian
Pengaturcaraan fungsional adalah seperti kereta berkuasa hidrogen - futuristik canggih, Tetapi ia tidak dipromosikan secara meluas . Berbeza dengan pengaturcaraan imperatif, ia terdiri daripada urutan pernyataan yang mengemas kini keadaan global pada masa pelaksanaan. Pengaturcaraan fungsional menukar pengiraan kepada penilaian ekspresi. Ungkapan ini semuanya terdiri daripada fungsi matematik tulen, yang merupakan kelas pertama (boleh digunakan dan diproses sebagai nilai biasa) dan tidak mempunyai kesan sampingan.
Nilai pengaturcaraan fungsional nilai berikut:
Fungsi adalah keutamaan pertama
Kita harus fungsi merawat Diperlakukan seperti objek kelas lain dalam bahasa pengaturcaraan. Dalam erti kata lain, anda boleh menyimpan fungsi dalam pembolehubah, mencipta fungsi secara dinamik dan mengembalikan fungsi atau menghantar fungsi kepada fungsi lain. Mari lihat contoh...
Rentetan boleh disimpan sebagai pembolehubah, dan begitu juga dengan fungsi, contohnya:
var sayHello = function() { return “Hello” };
Rentetan boleh disimpan sebagai medan objek, dan begitu juga dengan fungsi, contohnya:
var person = {message: “Hello”, sayHello: function() { return “Hello” }};
Rentetan boleh dibuat hanya apabila ia diperlukan lagi, dan sebagainya boleh fungsi, contohnya:
“Hello ” + (function() { return “World” })(); //=> Hello World
Rentetan boleh dihantar ke fungsi sebagai parameter input, dan fungsi itu juga boleh melakukannya:
function hellloWorld(hello, world) { return hello + world() }
Rentetan boleh digunakan sebagai nilai pulangan fungsi, dan fungsi itu juga boleh melakukannya, contohnya:
return “Hello”; return function() { return “Hello”};
Jika fungsi mengambil fungsi lain sebagai parameter input atau sebagai nilai pulangan, ia dipanggil fungsi tertib tinggi. Kami baru sahaja melihat contoh fungsi tertib lebih tinggi. Seterusnya, mari kita lihat situasi yang lebih kompleks.
Contoh 1:
[1, 2, 3].forEach(alert); // alert 弹窗显示“1" // alert 弹窗显示 "2" // alert 弹窗显示 "3”
Contoh 2:
function splat(fun) { return function(array) { return fun.apply(null, array); }; } var addArrayElements = splat(function(x, y) { return x + y }); addArrayElements([1, 2]); //=> 3
KegemaranFungsi tulen
Tulen fungsi tidak akan mempunyai kesan sampingan lain Apa yang dipanggil kesan sampingan merujuk kepada pengubahsuaian keadaan luaran fungsi yang disebabkan oleh fungsi. Contohnya:
Ubah suai pembolehubah
Ubah suai struktur data
Ubah suai pembolehubah daripada dunia luar Tetapkan medan
Buang pengecualian atau timbulkan mesej ralat
Contoh paling mudah ialah fungsi matematik. Fungsi Math.sqrt(4) sentiasa mengembalikan 2. Ia tidak akan menggunakan sebarang maklumat menyejukkan lain, seperti status atau parameter tetapan. Fungsi matematik tidak pernah menyebabkan sebarang kesan sampingan.
Pengaturcaraan fungsional menyokong fungsi tulen, yang tidak boleh mengubah data, jadi ia adalah kebanyakannya digunakan untuk mencipta data tidak berubah. Dengan cara ini, tidak perlu mengubah suai struktur data sedia ada dan ia boleh mencipta yang baharu dengan cekap.
Anda mungkin ingin tahu sama ada fungsi tulen menghasilkan nilai pulangan yang tidak berubah dengan menukar beberapa data setempat, adakah ia dibenarkan ? Jawapannya ya.
Sangat sedikit jenis data dalam JavaScript tidak boleh diubah secara lalai. Rentetan ialah contoh jenis data yang tidak boleh diubah:
var s = "HelloWorld"; s.toUpperCase(); //=> "HELLOWORLD" s; //=> "HelloWorld"
• Elakkan kekeliruan dan tingkatkan ketepatan program: Dalam sistem yang kompleks, Kebanyakan pepijat yang tidak jelas disebabkan oleh keadaan diubah suai oleh kod klien luaran dalam program.
• Wujudkan pengaturcaraan berbilang benang "pantas dan ringkas": jika berbilang rangkaian boleh mengubah suai nilai kongsi yang sama, anda perlu mendapatkan nilai secara serentak. Ini adalah cabaran pengaturcaraan yang membosankan dan terdedah kepada ralat untuk pakar.
Memori transaksi perisian dan model Actor menyediakan pemprosesan langsung pengubahsuaian dengan cara selamat benang.
Rekursi ialah teknik pengaturcaraan berfungsi yang paling terkenal. Jika anda belum mengetahuinya lagi, fungsi rekursif ialah fungsi yang memanggil dirinya sendiri.
替代反复循环的最经典方式就是使用递归,即每次完成函数体操作之后,再继续执行集合里的下一项,直到满足结束条件。递归还天生符合某些算法实现,比如遍历树形结构(每个树枝都是一颗小树)。
在任何语言里,递归都是一项重要的函数式编程方式。很多函数语言甚至要求的更加严格:只支持递归遍历,而不支持显式的循环遍历。这需要语言必须保证消除了尾端调用,这是 JavasSrip 不支持的。
数学定义了很多无穷集合,比如自然数(所有的正整数)。他们都是符号表示。任意特定有限的子集都在需要时求值。我们将其称之为惰性求值(也叫做非严格求值,或者按需调用,延迟执行)。及早求值会强迫我们表示出所有无穷数据,而这显然是不可能的。
很多语言都默认是惰性的,有些也提供了惰性数据结构以表达无穷集合,并在需要时对自己进行精确计算。
很明显一行代码 result = compute() 所表达的是将 compute() 的返回结果赋值给 result。但是 result 的值究竟是多少只有其被用到的时候才有意义。
可见策略的选择会在很大程度上提高性能,特别是当用在链式处理或者数组处理的时候。这些都是函数式程序员所喜爱的编程技术。
这就开创可很多可能性,包括并发执行,并行技术以及合成。
但是,有一个问题,JavaScrip 并不对自身进行惰性求值。话虽如此,Javascript 里的函数库可以有效地模拟惰性求值。
所有的函数式语言都有闭包,然而这个语言特性经常被讨论得很神秘。闭包是一个函数,这个函数有着对内部引用的所有变量的隐式绑定。换句话说,该函数对它引用的变量封闭了一个上下文。JavaScript 中的闭包是能够访问父级作用域的函数,即使父级函数已经调用完毕。
function multiplier(factor) { return function(number) { return number * factor; }; } var twiceOf = multiplier(2); console.log(twiceOf(6)); //=> 12
函数式编程是声明式的,就像数学运算,属性和关系是定义好的。运行时知道怎么计算最终结果。阶乘函数的定义提供了一个例子:
factorial(n) = 1 if n = 1
n * factorial(n-1) if n > 1
该定义将 factorial(n) 的值关联到 factorial(n-1),是递归定义。特殊情况下的 factorial(1) 终止了递归。
var imperativeFactorial = function(n) { if(n == 1) { return 1 } else { product = 1; for(i = 1; i <= n; i++) { product *= i; } return product; } } var declarativeFactorial = function(n) { if(n == 1) { return 1 } else { return n * factorial(n - 1); } }
从它实现阶乘计算来看,声明式的阶乘可能看起来像“命令式”的,但它的结构更像声明式的。
命令式阶乘使用可变值、循环计数器和结果来累加计算后的结果。这个方法显式地实现了特定的算法。不像声明式版本,这种方法有许多可变步骤,导致它更难理解,也更难避免 bug 。
有很多函数式库:underscore.js, lodash,Fantasy Land, Functional.js, Bilby.js, fn.js, Wu.js, Lazy.js, Bacon.js, sloth.js, stream.js, Sugar, Folktale, RxJs 等等。
map(), filter(), 和 reduce()函数 构成了函数式程序员工具包的核心。 纯高阶函数成了函数式方法的主力。事实上,它们是纯函数和高阶函数应该仿效的典型。它们用一个函数作为输入,返回没有副作用的输出。
这些 JavaScript 函数对每一个函数式程序来说都是至关重要的。他们可以去除循环和语句,使得代码更加整洁。这些都是实现 ECMAScript5.1 的浏览器的标准,他们只处理数组。每次调用都会创建创建并返回一个新的数组。已存在的数组不会被修改。但是稍等,事情很不止于此。。。他们还将函数作为输入参数,通常是作为回调的匿名函数。他们会遍历将整个数组并且将该回调函数应用与每一项!
myArray = [1,2,3,4];
newArray = myArray.map(function(x) {return x*2});
console.log(myArray); // Output: [1,2,3,4]
console.log(newArray); // Output: [2,4,6,8]
除了这三个函数,还有很多函数可以扎入到几乎每一个函数式应用里:
forEach(),concat(), reverse(), sort(), every() 以及some().
JavaScript sudah tentu bukan bahasa pengaturcaraan berfungsi dalam erti kata yang ketat, yang juga mendorong tumpuan pada paradigma lain Penggunaan:
Pengaturcaraan imperatif: pengaturcaraan berdasarkan huraian operasi terperinci
Pengaturcaraan berorientasikan objek berasaskan prototaip: berdasarkan objek prototaip dan Pengaturcaraan contoh
Metaprogramming: kaedah pengaturcaraan yang memanipulasi model pelaksanaan JavsScript. Takrifan metaprogram yang baik menerangkannya sebagai “Pengaturcaraan berlaku apabila anda menulis kod untuk melakukan sesuatu, manakala metaprogramming berlaku apabila anda menulis kod yang menyebabkan perubahan dalam cara sesuatu ditafsirkan
Di atas ialah kandungan menggunakan JavaScript untuk kemahiran pengaturcaraan berfungsi (1) translation_javascript Untuk kandungan yang lebih berkaitan, sila perhatikan laman web PHP Cina (m.sbmmt.com) 🎜>