新增了三个字符串函数,str_starts_with, str_ends_with, str_contains, PHP 的函数这么方便,很难想象竟然一直没有这几个。 str_starts_with 判断字符串是否以另一个字符串开头,在PHP7以及之前 $id = 'inv_abcdefgh'; $result = strpos($id, 'inv_') === 0; var_dump($result); // true PHP8 中可以直接这么写 $result = str_starts_with($id, 'inv_'); str_ends_with 判断字符串是否以另外一个字符串结尾,在 PHP7 及之前,比较麻烦,通常是这么写 $id = 'abcd_inv'; $result = strpos(strrev($id), strrev('_inv')) === 0; 或者 $result = substr($id, -1 * strlen('_inv')) === '_inv'; 或者上正则吧 $result = preg_match('/_inv$/', $id) === 1; 看起来都是比较麻烦的。PHP8 里面可以简化成下面这样了 $id = 'abcd_inv'; $result = str_ends_with($id, '_ind'); str_contains 字符串包含,PHP8 之前一般就是 strpos 来实现了 $url = 'https://example?for=bar'; $result = strpos($url, '?') !== FALSE; PHP8 就直接一点 $result = str_contains($url, '?');
Fold function in haskell
- 获取链接
- 电子邮件
- 其他应用
let’s first take a look at some list functions, and see what’s the characteristic they all share
sum
: computes the sum of the numbers of a structure;and
: returns the conjunction of a container of Bools;map
:map f xs
is the list obtained by applyingf
to each element ofxs
.
There three are all common list function, and act very differently, but can be defined recursively using pattern matching as follow:
mySum :: (Num t) => [t] -> t
mySum [] = 0 -- sum of empty is 0
mySum (x : xs) = x + mySum xs -- otherwise, add first element to sum of rest of the list
myAnd :: [Bool] -> Bool
myAnd [] = True -- and of empty is True
myAnd (x : xs) = x && myAnd xs -- otherwise, return the conjunction of first element and the rest of list
myMap :: (t -> t) -> [t] -> [t]
myMap _ [] = [] -- map any function to empty is empty
myMap f (x : xs) = f x : myMap f xs -- otherwise, prepends f of first element to map f of rest of list
Here we can see the common pattern: Each of them has a binary operator, a starting value (typically the right-identity of the operator), and a list:
- in
sum
function, they are+
, 0 and the list; - in
and
function, they are&&
,True
and the list; - in
map
function, things is a litter complicate, but we can still find them:(\x xs -> (f x):xs)
,[]
and the the list.
In Haskell
, we have a high order function which applied to a binary operator, a starting value (typically the right-identity of the operator), and a list, reduces the list using the binary operator, from right to left:
foldr f z [x1, x2, ..., xn] == x1 `f` (x2 `f` ... (xn `f` z)...)
So we can rewrite sum
, and
and map
use foldr
like this:
mySum' :: (Num t) => [t] -> t
mySum' xs = foldr (+) 0 xs
myAnd' :: [Bool] -> Bool
myAnd' xs = foldr (&&) True xs
myMap' :: (t -> t) -> [t] -> [t]
myMap' xs = foldr (\x xs -> (f x):xs) [] xs
It’s way much easier for us to understand.
That’s all for today, happy coding!
此博客中的热门博文
D3js Data-binding basics
We can use d3.select() to select and change DOM elements, and we can create and remove elements based on data. const books = [ 'Eloquent JavaScript' , 'JavaScript: The Good Parts' , 'JavaScript: The Definitive Guide' , 'You Don’t Know JS' ] d3.select( 'body' ).selectAll( 'div.books' ) .data(books) .enter() .append( 'div' ) .attr( 'class' , 'books' ) .html( function (d) { return d }) The result is: d3.selectAll() We start a selection using d3.selectAll() with a CSS identifier. Often there’s no elements match this identifier, and we then use .enter() function to create new elements. .data() We associate the data array with the elements which we selected using d3.selectAll() . For example we can access the first item of the array using code like this: document.getElementsByClassName( "books" )[ 0 ].__data__ .enter() and .exit() When we have more data items t
JavaScript 数据类型
类型 JavaScript 语言的每个值都属于一种数据类型。JavaScript 语言规定了7中类型: Undefined Null Boolean String Number Symbol (ES6开始加入) Object Undefined, Null Undefined 表示未定义,有一个值 undefined。任何变量在赋值是 Undefined 类型,值为 undefined。一般我们可以用全局变量 undefined 表示这个值,或者 void 运算符将任意表达式变成 undefined。undefined 是一个变量而非关键字,为了避免被无意中篡改,建议使用 void 0 来获取 undefined 值。 Null 表示“定义了但为空”,与 Undefined 有一定的表义差别。Null类型只有一个值 null,它是语言关键字,在任何代码中都可以使用 null 来获得 null 值。 实际代码中,不要将变量赋值为 undefined,这样可保证所有值为 undefined 的变量,都是从来未赋值状态。 Boolean Boolean 类型有两个值,true 和 false,表示真和假,均为语言关键字。 String String 表示文本数据,最大长度为 2 53 - 1。 String 的意义并非“字符串”,而是字符串的 UTF-16 编码,字符串的最大长度,受编码长度影响。 JavaScript 字符串是不可变量,构造之后没有任何方法变更内容,具有值类型的特征。 JavaScript 将每个 UTF-16 单元作为一个字符,处理非 BMP(超出 U+000 ~ U+FFF范围)字符是,需要格外小心。 Number Number 类型有 18437736874454810627(即 2 64 - 2 53 +3)个值,基本符合 IEEE 754-2008 规定的双精度浮点数规则,除了一下例外: NaN,占用 9007199254740990,这是原来符合 IEEE 规则的数字 Infinity,无穷大 -Infinity,负无穷大 JavaScript中,+0 和 -0 在加法中无差别,在除法中有差别。1/+0 、1/-0 分别得到 Infinity 和 -Infinity。
Vue3新特性(1) —— Vite
Vite (法语 fast )是 Vue3 的默认构建工具,在开发环境下基于浏览器原生 ES module 开发,从而实现按需编译,在生产环境下基于 Rollup 打包。它具有如下几个特点: 快速的冷启动 即时的热模块更新 真正的按需编译 开始使用 终端执行 $ npm init vite-app vite-example 生成一个 vite 项目,结构如下 ├── index.html ├── package.json ├── public │ └── favicon.ico └── src ├── App.vue ├── assets │ └── logo.png ├── components │ └── HelloWorld.vue ├── index.css └── main.js 进入项目目录,执行 $ cd vite-example $ npm install && npm run dev 可以看到dev server启动速度非常快,大概2s不到 vite 特性 打开chrome的开发工具,看到浏览器直接加载了 vue 文件,后面跟了参数 type 看下源代码的 main.js import { createApp } from 'vue' import App from './App.vue' import './index.css' createApp(App).mount('#app') 对比一下浏览器返回的 main.js import { createApp } from '/@modules/vue.js' import App from '/src/App.vue' import '/src/index.css?import' createApp(App).mount('#app') 对vue引用转化为/@modules/vue.js 对./App.vue转换为/src/App.vue 对./index.css转化为/src/index.css
评论