ECMAScript 2016(ES7)
Exponentiation Operator (**)
指数运算符,用于计算数字的幂运算,是 Math.pow()
的语法糖。
javascript
{
// 传统方法:自定义函数
function pow(x, y) {
let result = 1
for (let i = 0; i < y; i++) {
result *= x
}
return result
}
console.log(pow(2, 5)) // 32
// 传统方法:Math.pow()
console.log(Math.pow(2, 5)) // 32
console.log(Math.pow(3, 3)) // 27
console.log(Math.pow(10, -2)) // 0.01
// ES7 新语法:指数运算符
console.log(2 ** 5) // 32
console.log(3 ** 3) // 27
console.log(10 ** -2) // 0.01
// 运算符优先级
console.log(2 ** 3 ** 2) // 512 (等同于 2 ** (3 ** 2))
console.log((2 ** 3) ** 2) // 64
// 与其他运算符结合
console.log(2 ** 3 * 4) // 32 (等同于 (2 ** 3) * 4)
console.log(2 * 3 ** 2) // 18 (等同于 2 * (3 ** 2))
// 赋值运算符形式
let num = 2
num **= 3
console.log(num) // 8
// 实际应用:数学计算
function calculateCompoundInterest(principal, rate, time) {
return principal * (1 + rate) ** time
}
const investment = calculateCompoundInterest(1000, 0.05, 10)
console.log(investment.toFixed(2)) // 1628.89
// 计算圆的面积
function circleArea(radius) {
return Math.PI * radius ** 2
}
console.log(circleArea(5).toFixed(2)) // 78.54
// 计算立方体体积
function cubeVolume(side) {
return side ** 3
}
console.log(cubeVolume(4)) // 64
// 科学计算:计算距离
function distance3D(x1, y1, z1, x2, y2, z2) {
return Math.sqrt((x2 - x1) ** 2 + (y2 - y1) ** 2 + (z2 - z1) ** 2)
}
console.log(distance3D(0, 0, 0, 3, 4, 5).toFixed(2)) // 7.07
// 二进制运算
function powerOfTwo(n) {
return 2 ** n
}
console.log([0, 1, 2, 3, 4, 5].map(powerOfTwo)) // [1, 2, 4, 8, 16, 32]
// 处理大数
console.log(10 ** 6) // 1000000
console.log(2 ** 53) // 9007199254740992 (Number.MAX_SAFE_INTEGER + 1)
console.log(2 ** 10) // 1024 (1KB)
console.log(2 ** 20) // 1048576 (1MB)
// 分数指数(开方)
console.log(9 ** 0.5) // 3 (平方根)
console.log(8 ** (1/3)) // 2 (立方根)
console.log(16 ** 0.25) // 2 (四次方根)
// 与 BigInt 结合使用
console.log(2n ** 100n) // 1267650600228229401496703205376n
// 性能比较
function performanceTest() {
const start1 = performance.now()
for (let i = 0; i < 1000000; i++) {
Math.pow(2, 10)
}
const end1 = performance.now()
const start2 = performance.now()
for (let i = 0; i < 1000000; i++) {
2 ** 10
}
const end2 = performance.now()
console.log(`Math.pow(): ${end1 - start1}ms`)
console.log(`** operator: ${end2 - start2}ms`)
}
// performanceTest() // ** 运算符通常更快
}
Array.prototype.includes()
判断数组是否包含指定值,返回布尔值,比 indexOf()
更语义化。
javascript
{
const numbers = [1, 2, 3, 4, 5, NaN]
const fruits = ['apple', 'banana', 'orange']
// 基本用法
console.log(numbers.includes(3)) // true
console.log(numbers.includes(6)) // false
console.log(fruits.includes('apple')) // true
// 与 indexOf() 的比较
console.log(numbers.indexOf(3) !== -1) // true (传统方法)
console.log(numbers.includes(3)) // true (ES7 方法,更直观)
// 处理 NaN
console.log(numbers.indexOf(NaN)) // -1 (indexOf 无法正确处理 NaN)
console.log(numbers.includes(NaN)) // true (includes 可以正确处理 NaN)
// 使用 fromIndex 参数
const array = [1, 2, 3, 4, 5, 3, 2, 1]
console.log(array.includes(3)) // true
console.log(array.includes(3, 3)) // true (从索引 3 开始查找)
console.log(array.includes(3, 6)) // false (从索引 6 开始查找)
// 负数索引
console.log(array.includes(2, -3)) // true (从倒数第3个位置开始)
console.log(array.includes(1, -1)) // true (从最后一个位置开始)
// 实际应用:条件判断
const userRoles = ['admin', 'editor', 'viewer']
const currentUser = { role: 'editor' }
if (userRoles.includes(currentUser.role)) {
console.log('User has valid role')
}
// 表单验证
function validateEmail(email) {
const validDomains = ['gmail.com', 'yahoo.com', 'hotmail.com']
const domain = email.split('@')[1]
return validDomains.includes(domain)
}
console.log(validateEmail('user@gmail.com')) // true
console.log(validateEmail('user@unknown.com')) // false
// 过滤数组
const allUsers = [
{ name: 'Alice', status: 'active' },
{ name: 'Bob', status: 'inactive' },
{ name: 'Charlie', status: 'pending' },
{ name: 'Diana', status: 'active' }
]
const activeStatuses = ['active', 'pending']
const filteredUsers = allUsers.filter(user =>
activeStatuses.includes(user.status)
)
console.log(filteredUsers)
// [{ name: 'Alice', status: 'active' }, { name: 'Charlie', status: 'pending' }, { name: 'Diana', status: 'active' }]
// 权限检查
class PermissionManager {
constructor(userPermissions) {
this.permissions = userPermissions
}
hasPermission(permission) {
return this.permissions.includes(permission)
}
hasAnyPermission(permissions) {
return permissions.some(permission => this.permissions.includes(permission))
}
hasAllPermissions(permissions) {
return permissions.every(permission => this.permissions.includes(permission))
}
}
const pm = new PermissionManager(['read', 'write', 'delete'])
console.log(pm.hasPermission('read')) // true
console.log(pm.hasPermission('admin')) // false
console.log(pm.hasAnyPermission(['admin', 'read'])) // true
console.log(pm.hasAllPermissions(['read', 'write'])) // true
// 黑名单检查
function isValidUrl(url) {
const blockedDomains = ['spam.com', 'malware.net', 'phishing.org']
const domain = new URL(url).hostname
return !blockedDomains.includes(domain)
}
console.log(isValidUrl('https://google.com')) // true
console.log(isValidUrl('https://spam.com')) // false
// 菜单项激活状态
function getActiveMenuItems(currentPath, menuItems) {
return menuItems.map(item => ({
...item,
active: item.paths.includes(currentPath)
}))
}
const menuItems = [
{ name: 'Home', paths: ['/', '/home'] },
{ name: 'About', paths: ['/about', '/about-us'] },
{ name: 'Contact', paths: ['/contact', '/contact-us'] }
]
const activeItems = getActiveMenuItems('/about', menuItems)
console.log(activeItems)
// 搜索功能
function searchUsers(query, users) {
const keywords = query.toLowerCase().split(' ')
return users.filter(user =>
keywords.every(keyword =>
user.name.toLowerCase().includes(keyword) ||
user.tags.some(tag => tag.toLowerCase().includes(keyword))
)
)
}
const users = [
{ name: 'John Doe', tags: ['developer', 'javascript'] },
{ name: 'Jane Smith', tags: ['designer', 'ui/ux'] },
{ name: 'Bob Johnson', tags: ['developer', 'python'] }
]
const searchResults = searchUsers('john developer', users)
console.log(searchResults) // [{ name: 'John Doe', tags: ['developer', 'javascript'] }]
// 限制:只能检测简单类型
const complexArray = [
{ id: 1, name: 'Alice' },
{ id: 2, name: 'Bob' },
[1, 2, 3]
]
console.log(complexArray.includes({ id: 1, name: 'Alice' })) // false (对象引用不同)
console.log(complexArray.includes([1, 2, 3])) // false (数组引用不同)
// 解决复杂类型的检查
function includesObject(array, target, key) {
return array.some(item => item[key] === target[key])
}
console.log(includesObject(complexArray, { id: 1, name: 'Alice' }, 'id')) // true
function includesArray(array, target) {
return array.some(item =>
Array.isArray(item) &&
Array.isArray(target) &&
item.length === target.length &&
item.every((val, index) => val === target[index])
)
}
console.log(includesArray(complexArray, [1, 2, 3])) // true
}