首页
学习
活动
专区
圈层
工具
发布
首页
学习
活动
专区
圈层
工具
MCP广场
社区首页 >专栏 >JavaScript 异步编程

JavaScript 异步编程

作者头像
用户3045442
发布于 2020-07-31 02:27:39
发布于 2020-07-31 02:27:39
1.4K00
代码可运行
举报
文章被收录于专栏:Android研究院Android研究院
运行总次数:0
代码可运行

❝掌握JavaScript主流的异步任务处理 ( 本篇文章内容输出来源:《拉钩教育大前端训练营》参阅《你不知道的JavaScript中卷》异步章节)❞

JavaScrip 采用单线程模式工作的原因,需要进行DOM操作,如果多个线程同时修改DOM浏览器无法知道以哪个线程为主。

JavaScirpt分为:同步模式、异步模式

同步模式与异步模式

同步模式

同步模式其实就是:排队执行,下面根据一个Gif动画来演示同步模式,非常简单理解,js维护了一个正在执行的工作表,当工作表的任务被清空后就结束了。

如下打开调试模式,注意观察Call Stack调用栈的情况,当执行foo方法的是否foo会进入Call Stack调用栈之后打印'foo task',然后执行bar()方法bar进入调用栈打印'bar task',bar执行完后被移除调用栈,foo被移除调用栈然后打印'global end'执行结束。

1.gif

存在的问题:如果其中的某一个任务执行的时间过长,后面的任务就会被阻塞,界面就会被卡顿,所以就需要使用异步模式去执行避免界面被卡死。

异步模式

通过一个图来演示异步任务,用到事件循环与消息队列机制实现

Untitled 0.png

Promise异步方案

常见的异步方案就是通过回调函数来实现,导致回调地狱的问题,CommonJS社区提出了Promise方案并在ES6中采用了。如下代码实现一个环绕动画如果通过回调会嵌套多次。

案例演示地址

代码语言:javascript
代码运行次数:0
运行
AI代码解释
复制
let box = document.querySelector('#box');
    move(box, 'left', 300, () => {
        move(box, 'top', 300, () => {
            move(box, 'left', 0, () => {
                move(box, 'top', 0, () => {
                    console.log('运动完成');
                });
            });
        });
    });

Promise 的使用案例演示代码如下:

代码语言:javascript
代码运行次数:0
运行
AI代码解释
复制
//应用案例
function ajax(url) {
    return new Promise(function (resolve, reject) {
        var xhr = new XMLHttpRequest();
        xhr.open('GET', url);
        xhr.responseType = 'json';
        xhr.onload = function () {
            if (this.status === 200) {
                resolve(this.response);
            } else {
                reject(new Error(this.statusText));
            }
        }
        xhr.send();
    });
}

let promise2 = ajax('./api/user.json');
let newPromise = promise2.then((res) => {
    console.log(res);
});
console.log(promise2 === newPromise);//false 每一个then都返回一个新的promise对象
//then 仍然会导致回调地狱 尽量保证异步任务的扁平化

//也可以在then方法中返回一个promise对象
ajax('./api/user.json').then(res=>{
    console.log(111);
    return ajax('./api/user.json');
}).then(res=>{
    console.log(222);
    return 'foo';
}).then(res=>{
    console.log(res);
})

//OUT:
false
Array(2)
111
222
foo

Promise 链式调用注意一下几点

  • Promise对象的then方法会返回一个全新的Promise对象
  • 后面的then方法就是在为上一个then返回的Promise注册回调
  • 前面then方法中回调函数的返回值会作为后面then方法回调的参数
  • 如果回调中返回的是Promise,那后面then方法的回调会等待它的结束

Promise异常处理

Promise 执行过程中出现错误onRejected回调会执行,一般通过catch方法注册失败回调,跟在then方法第二个参数注册回调结果是一样的。

代码语言:javascript
代码运行次数:0
运行
AI代码解释
复制
const promise = new Promise(function (resolve, reject) {
    //只能调用两者中的一个 一旦设置了某个状态就不允许修改了
    // resolve(100);//成功
    reject(new Error('promise rejected'));//失败
});

promise.then(function (value) {
    console.log('resolved', value);
}, function (err) {
    console.log('rejected', err);
}).catch(err=>{
    console.log("catch",err);
});

console.log('end');

推荐使用catch方法作为错误的回调,不推荐使用then方法的第二个参数作为错误回调,原因如下:

当我们在收到正确的回调又返回一个Promise对象但是在执行过程中出现了错误,而这时无法收到错误回调的。

代码语言:javascript
代码运行次数:0
运行
AI代码解释
复制
ajax('./api/user.json').then(res=>{
    console.log('onresolved',res);
    return ajax('/error.json');
},err=>{
    console.log("onRejected",err);
});

我们再来看catch方法:

代码语言:javascript
代码运行次数:0
运行
AI代码解释
复制
ajax('./api/user.json').then(res=>{
    console.log('onresolved',res);
    return ajax('/error.json');
}).catch(err=>{
    console.log("onRejected",err);
});

打印结果如下:catch方法可以捕捉到then方法return的新的Promise对象的执行错误。

代码语言:javascript
代码运行次数:0
运行
AI代码解释
复制
onresolved (2) [{}, {}]
onRejected Error: Not Found
    at XMLHttpRequest.xhr.onload (promise.js:28)

除此之外全局对象注册unhandlerdrejection 事件,处理代码中没有被手动捕获处理的异常。下面是node中的方法

代码语言:javascript
代码运行次数:0
运行
AI代码解释
复制
process.on('unhandledRejection',(reason,promise)=>{
    //reason => Promise 失败原因,一般是一个错误对象
  //promise => 出现异常的Promise对象
})

一般不推荐使用,应该在代码中明确捕获每一个可能的异常,而不是丢给全局处理

Promise 的静态方法

代码语言:javascript
代码运行次数:0
运行
AI代码解释
复制
//一个成功状态的Promise 对象
Promise.resolve('foo').then(res=>{
    console.log(res);
});
var promise = ajax('./api/user.json');

var promise2 = Promise.resolve(promise);//如果传入一个Prmose对象会原样返回相同的Promise对象

console.log(promise === promise2);//true

//如下传入的一个对象带有then方法的对象一样可以执行
Promise.resolve({
    then:function(onFulfilled,onRejected){
        onFulfilled('f00');
    }
}).then(res=>{
    console.log(res);//f00
});

//创建一个失败状态的Promise对象
Promise.reject(new Error('rejected')).catch(err=>{
    console.log(err);
})

Promise并行执行:all race 将多个Promise对象组合到一起

代码语言:javascript
代码运行次数:0
运行
AI代码解释
复制
var promise = Promise.all([ajax('./api/user.json'),ajax('./api/user.json')]);

promise.then(res=>{
    console.log(res);
})
//都成功才会成功 有一个失败就会返回失败状态回调
ajax('./api/user.json')
.then(res=>{
    const urls = Object.values(res);
    console.log('??',urls);
    const tasks = urls.map(url=>{
        console.log(url);
        return ajax(url);
    });
    console.log(tasks);
    return Promise.all(tasks);
}).then(res=>{
    console.log(res);
});

//race 只会等待第一个结束的任务
const request = ajax('./api/user.json');

const timeout = new Promise((resolve,reject)=>{
    setTimeout(() => {
        reject(new Error('timeout'));
    }, 500);
});

Promise.race([request,timeout]).then(res=>{
    console.log(res);
}).catch(err=>{
    console.log(err);    
});

模仿网络慢的情况,可以看到race会执行reject

Untitled 1.png

Promise 执行时序:宏任务与微任务

Promise的回调会作为微任务执行。微任务:提高整体的响应能力。目前大部分异步回调作为宏任务

常见的宏任务与微任务如下图所示:

Untitled 2.png

下面是JavaScript执行异步任务的执行时序图:

Untitled 3.png

看下面的例子来进行理解: 下列例子中输出: 2 4 1 3 5

这其实也符合了上图事件循环的原理,先主任务执行输出: 2 4 之后查询是否有微观任务没有就新建宏观任务执行

然后宏观任务执行输出:1 3

之后查询是否之后查询是否有微观任务没有就新建宏观任务执行

执行输出: 5

代码语言:javascript
代码运行次数:0
运行
AI代码解释
复制
let time = 0;
    setTimeout(()=>{
        time = 1;
        console.log(time);
        //宏任务嵌套宏任务
        setTimeout(()=>{
            time = 5;
            console.log(time);
        },1000);
    },1000);
    time = 2;
    console.log(time);
    setTimeout(()=>{
        time=3;
        console.log(time);
    },1000);
    time = 4;
    console.log(time);

下面我们在看一个带有微任务的例子: 下面例子输出的结果: 2 4 6 1 3 5.主任务执行完毕之后先执行微任务.

代码语言:javascript
代码运行次数:0
运行
AI代码解释
复制
let time = 0;
    setTimeout(()=>{
        time = 1;
        console.log(time);
        //宏任务嵌套宏任务
        setTimeout(()=>{
            time = 5;
            console.log(time);
        },1000);
    },1000);
    time = 2;
    console.log(time);
    setTimeout(()=>{
        time=3;
        console.log(time);
    },1000);
    time = 4;
    console.log(time);
    //微任务
    let observer = new MutationObserver(()=>{
        time = 6;
        console.log(6);
    });
    observer.observe(document.body,{
        attributes:true
    });
    document.body.setAttribute('kkb',Math.random());

Generator异步方案

首先需要连接一下迭代器的

「迭代器」

❝for...in : 以原始插入的顺序迭代对象的可枚举属性for...of : 根据迭代对象的迭代器具体实现迭代对象数据 可迭代对象 - 实现了[Symbol.iterator]方法数组结构有[Symbol.iterator]方法,但是如果要迭代Object就需要添加[Symbol.iterator]方法的实现如下代码: ❞

代码语言:javascript
代码运行次数:0
运行
AI代码解释
复制
<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <title>Document</title>
</head>
<body>
</body>
<script>
    //for of/ for in 迭代器
    //for...in : 以原始插入的顺序迭代对象的可枚举属性
    //for...of : 根据迭代对象的迭代器具体实现迭代对象数据 可迭代对象 - 实现了[Symbol.iterator]方法
    let arr = ['a','b','c','d'];
    let obj = {
        a:1,
        b:2,
        c:3
    }
    for(let attr in arr){
        console.log(attr);//0 1 2 3
    }
    for(let val of arr){
        console.log(val);//a b c d
    }
    console.dir(arr);//symbol(Symbol.iterator): ƒ values()
    console.dir(obj);//没有Symbol.iterator方法
    
    //如果要对象使用for of需要加一个属性 自定义迭代器
    obj[Symbol.iterator] = function(){
        //迭代协议
        //将对象value转换为数组
        let values = Object.values(obj);
        //将对象key转为数组
        let keys = Object.keys(obj);
        // let values = [...obj];
        console.log(values);
        let index = 0;
        //必须返回一个对象 同时必须有一个next方法
        return {
            next(){
                //done:表示循环是否完成
                //value:for a of obj a就是value
                //必须返回一个对象
                if (index >= values.length) {
                    return{
                        done:true
                    }
                }else{
                    return{
                        done:false,
                        value:{
                            key:keys[index],
                            value:obj[keys[index++]]
                        }
                    }
                }
            }
        }
    }
    //可以测试直接迭代方法
    let objIterator = obj[Symbol.iterator]();
    //执行next方法
    console.log(objIterator.next());
    
    //其实for...of 一直调用objIterator.next() 直到done:true就会停止
    for(let o of obj){
        //obj is not iterable
        console.log(o);
    }
</script>
</html>

❝Generator函数比普通函数多了一个*号,函数内部使用yield语句,定义遍历器的每个成员,即不同的内部状态. 实现可迭代的函数.Generator函数一般很少会使用了解即可. ❞

代码语言:javascript
代码运行次数:0
运行
AI代码解释
复制
<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <title>Document</title>
</head>
<body>
</body>
<script>
    /**
     * 定义可迭代函数 yield 每次迭代的返回值 
     */
    function* fn() {
        yield new Promise((resolve, reject) => {
            setTimeout(() => {
                console.log("a");
                resolve("1");
            }, 500);
        });
        yield new Promise((resolve, reject) => {
            setTimeout(() => {
                console.log("b");
                resolve("2");
            }, 500);
        });
        yield new Promise((resolve, reject) => {
            setTimeout(() => {
                console.log("c");
                resolve("3");
            }, 500);
        });
    }
    let f = fn();
    // console.log(f.next());
    // for (const iterator of f) {
    //     console.log(iterator);
    // }
    function co(fn) {
        let f = fn();
        next();
        function next(data){
            let result = f.next();
            console.log(result);
            if(!result.done){
                //上一个异步执行完毕
                result.value.then((info)=>{
                    console.log(info,data);
                    next(info);
                });
            }
        }
    }
    co(fn);
    // for (let fn of f) { 一同执行 不能异步调用
    // }
</script>
</html>

Generator 生成器函数的使用

代码语言:javascript
代码运行次数:0
运行
AI代码解释
复制
//Generator 生成器函数
function* foo() {
    try {
        console.log('start');
        const res = yield 'foo';
        console.log(res);
    } catch (e) {
        console.log(e);
    }

}

const generator = foo();

const result = generator.next();

console.log(result);

generator.next('bar');

generator.throw(new Error('Generator Error'));//抛出一个异常

Generator 异步使用的案例如下代码:

代码语言:javascript
代码运行次数:0
运行
AI代码解释
复制
function* main() {
    try{
        const users = yield ajax('./api/user.json');
        console.log(users);
        const posts = yield ajax('./api/user.json');
        console.log(posts);
    }catch(e){
        console.log(e);
    }
}
//通用的异步生成器方法
function co(generator){
    const g = generator();
    function handleResult(result){
        if(result.done) return;
        result.value.then(data=>{
            handleResult(g.next(data));
        }).catch(err=>{
            g.throw(err);
        })
    }
    handleResult(g.next());
}

co(main);

Async/Await 语法糖

推荐使用异步编程的标准.需要注意await 后面必须是一个Promise对象,await只能出现在async函数内部目前还不支持(以后可能会支持)

代码语言:javascript
代码运行次数:0
运行
AI代码解释
复制
async function  main2() {
    try{
        const users = await ajax('./api/user.json');
        console.log(users);
        const posts = await ajax('./api/user.json');
        console.log(posts);
    }catch(e){
        console.log(e);
    }
}
main2();

Promise 源码手写实现

代码语言:javascript
代码运行次数:0
运行
AI代码解释
复制
1. Promise 是一个类 在执行这个类的时候 需要传递一个执行器进去 这个执行器会立即执行
2. Promise 中有三种状态分别为:pending -> fulfilled pending->rejected
3. resolve reject 函数用来更改状态
    resolve:fulfilled
    reject:rejected
4. then方法内部做的事情就是判断状态 如果状态成功调用成功回调函数
如果状态失败就回调失败的回调函数
5. then成功或失败都有一个参数分别表示成功的值和失败的原因
6. 记录成功的值和失败的值
7. 处理执行器内部异步情况的处理 调用resolve或reject
8. 处理then方法可以被多次调用
9. then方法可以被链式调用 后面then方法回调函数拿到的值是上一个then方法
回调函数的返回值
10. then 返回值是普通值还是Promise对象
11. then 返回相同的Promise对象循环调用的判断
12. 执行器内部发生错误 回调给reject,then 内部发生错误的处理
13. then无参数的链式调用实现
14. all等静态方法实现
代码语言:javascript
代码运行次数:0
运行
AI代码解释
复制

const PENDING = 'pending';//等待
const FULFILLED = 'fulfilled';//成功
const REJECTED = 'rejected';//失败

class MyPromise {
    constructor(executor) {
        try {
            executor(this.resolve, this.reject);//执行器立即执行
        } catch (e) {
            this.reject(e);
        }
    }
    status = PENDING;//定义状态
    //成功之后的值
    value = undefined;
    //失败之后的值
    error = undefined;

    //成功回调
    onFulfilled = [];
    //失败回调
    onRejected = [];
    //箭头函数 this指向不会被更改 this还会指向MyPromise对象
    resolve = (value) => {
        //0 判断状态是不是pending 阻止向下执行
        if (this.status !== PENDING) {
            return;
        }

        //1 状态更改
        this.status = FULFILLED;
        //2 保存成功之后的值
        this.value = value;
        //3 成功回调是否存在
        // this.onFulfilled && this.onFulfilled(this.value);
        while (this.onFulfilled.length) {
            this.onFulfilled.shift()();
        }
    }
    reject = (error) => {
        //0 判断状态是不是pending 阻止向下执行
        if (this.status !== PENDING) {
            return;
        }
        //1 状态更改
        this.status = REJECTED;
        //2 保存失败之后的值
        this.error = error;
        //3 失败回调是否存在
        // this.onRejected && this.onRejected(this.error);
        while (this.onRejected.length) {
            this.onRejected.shift()();
        }
    }
    then(onFulfilled, onRejected) {
        onFulfilled = onFulfilled ? onFulfilled : value => value;
        onRejected = onRejected ? onRejected : error => { throw error };
        //1. 实现链式调用
        let p = new MyPromise((resolve, reject) => {
            if (this.status === FULFILLED) {
                setTimeout(() => {
                    try {
                        //拿到回调函数的返回值
                        let result = onFulfilled(this.value);
                        //传递给下一个Promise对象
                        //判断result是普通值还是Promise对象
                        //如果是普通值 直接调用resolve
                        //如果是promise对象 查看promise对象返回的结果
                        //再根据promise对象返回的结果 决定调用resolve还是reject
                        // resolve(result);
                        //需要等待同步代码执行完毕拿到p在执行
                        this.resolvePromise(p, result, resolve, reject);
                    } catch (e) {
                        reject(e);
                    }
                }, 0);
            } else if (this.status == REJECTED) {
                setTimeout(() => {
                    try {
                        //拿到回调函数的返回值
                        let result = onRejected(this.error);
                        this.resolvePromise(p, result, resolve, reject);
                    } catch (e) {
                        reject(e);
                    }
                }, 0);
            } else {
                //由于异步代码没有立即执行 先存储回调 等异步代码执行完成后再执行回调
                this.onFulfilled.push(() => {
                    setTimeout(() => {
                        try {
                            //拿到回调函数的返回值
                            let result = onFulfilled(this.value);
                            this.resolvePromise(p, result, resolve, reject);
                        } catch (e) {
                            reject(e);
                        }
                    }, 0);
                });
                this.onRejected.push(() => {
                    setTimeout(() => {
                        try {
                            //拿到回调函数的返回值
                            let result = onRejected(this.error);
                            this.resolvePromise(p, result, resolve, reject);
                        } catch (e) {
                            reject(e);
                        }
                    }, 0);
                });
            }
        });
        return p;
    }
    resolvePromise(p, result, resolve, reject) {
        if (p === result) {
            return reject(new TypeError('TypeError: Chaining cycle detected for'));
        }
        if (result instanceof MyPromise) {
            //Promise对象 把新的Promise对象的值传递下去
            result.then(resolve, reject);
        } else {
            //普通值
            resolve(result);
        }
    }
    static all(array) {
        let result = [];
        let index = 0;
        return new MyPromise((resolve, reject) => {
            function addData(key, value) {
                result[key] = value;
                index++;
                if (index === array.length) {
                    //需要等待异步操作完成再调用resolve
                    resolve(result);
                }
            }
            for (let i = 0; i < array.length; i++) {
                let cur = array[i];
                if (cur instanceof MyPromise) {
                    cur.then((value) => {
                        addData(i, value);
                    }, (err) => {
                        reject(err);
                    });
                } else {
                    addData(i, cur);
                }
            }
        });
    }
    static resolve(value) {
        if (value instanceof MyPromise) {
            return value;
        }
        return new MyPromise((resolve, reject) => {
            resolve(value);
        });
    }
    static reject(error){
        return new MyPromise((resolve,reject)=>{
            reject(error);
        })
    }
    finally(callback){
        return this.then(res=>{
            return MyPromise.resolve(callback()).then(()=>res);
        },err=>{
            return MyPromise.resolve(callback()).then(()=>{throw err});
        });
    }
    catch(error){
        return this.then(undefined,error);
    }
}

//
module.exports = MyPromise;
本文参与 腾讯云自媒体同步曝光计划,分享自微信公众号。
原始发表:2020-07-28,如有侵权请联系 cloudcommunity@tencent.com 删除

本文分享自 Android研究院 微信公众号,前往查看

如有侵权,请联系 cloudcommunity@tencent.com 删除。

本文参与 腾讯云自媒体同步曝光计划  ,欢迎热爱写作的你一起参与!

评论
登录后参与评论
暂无评论
推荐阅读
编辑精选文章
换一批
【玩转云服务器】Linux(CentOS)挂载数据盘(小于2T)
将网站文件,数据库等信息放在数据盘中,万一需要重装系统时,数据还在。就像我们的电脑,把资料放在D盘,重装C盘后资料还在一样。安全又方便。
参谋带个长
2022/04/26
3.5K0
【玩转云服务器】Linux(CentOS)挂载数据盘(大于2T)
将网站文件,数据库等信息放在数据盘中,万一需要重装系统时,数据还在。就像我们的电脑,把资料放在D盘,重装C盘后资料还在一样。安全又方便。
参谋带个长
2022/04/29
3.9K0
Linux 格式化和挂载数据盘 转
本文描述如何用一个新的数据盘创建一个单分区数据盘并挂载文件系统。本文仅适用于使用 fdisk 命令对一个不大于 2 TB 的数据盘执行分区操作。如果需要分区的数据盘大于 2 TB,请参考 32TB 块存储分区。
wuweixiang
2018/08/14
4K0
CentOS 7.x 系统新数据盘分区挂载教程
好了,控制台层面的挂载就结束了;但是硬盘要能使用,还得到服务器内在系统层面进行挂载;
夏日萤火
2019/07/24
4.1K0
【Linux入门】磁盘分区、格式化
在进行磁盘管理操作时,必须慎重,要清楚自己在做什么。建议在操作之前对文件进行备份,或创建硬盘的快照、镜像,以便在出现意外时,最大限度的恢复数据。
参谋带个长
2023/12/19
3.4K0
咖啡康乐安装配置教程分配虚拟主机
SSH链接 (电脑软件推荐 Linux系统服务器远程SSH管理工具使用教程(FinalShell篇)
雾海梦曦
2022/11/04
9910
咖啡康乐安装配置教程分配虚拟主机
如何在家中部署服务器
我们可以使用rufus烧录镜像,选择下载的.iso镜像,选择烧录到的U盘,开始,中间如果杀毒软件报警,请放行。
逍遥子大表哥
2025/07/28
1360
如何在家中部署服务器
Centos7 初始化硬盘分区、挂载
刚刚在腾讯云买了一台服务器,刚买的服务器的数据盘都是需要自己来分区的,下面就记录一下操作。 通过命令fdisk-l查看硬盘信息 可以看到有两块硬盘/dev/vda和/dev/vdb,启动vda是系
晓晨
2018/06/22
4.8K0
centos怎么挂载数据盘并开机自启
第三步挂载到home挂载点,本文以/home为例:<strong>mount /dev/vdb1 /home</strong>
拾光博客
2024/04/03
3870
centos怎么挂载数据盘并开机自启
腾讯云轻量服务器挂载数据盘
前段时间新购入数据盘,发现一直没用到,因此通过参考~网络攻略~(百度),了解如何挂载数据盘,操作也极其简单
公爵
2022/09/28
19.1K0
腾讯云轻量服务器挂载数据盘
Linux挂载数据盘操作代码和一键挂载代码
除了上述一步步操作的方法以外,你如果部署宝塔环境的话,还可以直接使用下方一键挂载宝塔数据盘到/www的代码:
Yangsh888
2022/04/05
2K0
分区
原文https://ecloud.10086.cn/op-help-center/show/F230B8AC46DA76B8
用户5166330
2021/02/04
2.6K0
分区
Linux系统中的系统盘和数据盘是什么意思?
在Linux系统中,系统盘和数据盘是指存储设备的两种不同用途。系统盘通常用于安装操作系统和存储系统文件,而数据盘用于存储用户数据和应用程序等信息。本文将详细介绍系统盘和数据盘的定义、区别以及在Linux系统中的应用。
网络技术联盟站
2023/07/22
3.2K0
Linux系统中的系统盘和数据盘是什么意思?
腾讯云服务器CVM挂载云硬盘数据盘独立存储与系统盘分离
老蒋最近有空就在整理常规VPS、服务器数据盘与系统盘的挂载事宜。而且针对不同的服务商确实还是稍有不同,主要是公司最近有一个客户项目数据比较大,而且便于迁移和存储建议使用挂载数据盘中,以便以后的扩展增容。以前公司的所有项目默认50GB就足够使用,且这么大的硬盘对于大部分用户来说也是够用的,但是有些确实是鉴于系统的安全和数据盘和系统盘的分离需要隔离。
老蒋
2018/09/12
27.3K1
linux 云服务器挂载云盘
修改配置文件 vim /etc/fstab UUID=fadf579f-fe04-4e58-8811-07dd778aa8a1 /data ext4 defaults 0 0
用户1685462
2021/07/23
29.8K0
记录一次腾讯云轻量挂载数据盘的过程
本文将以 CentOS 8.0 操作系统为例,不同操作系统的格式化操作可能不同,本文仅供参考。
用户6935112
2022/08/01
2.1K0
Linux云服务器数据盘扩容教程(MBR分区)
本教程讲解 MBR 分区下的Linux CentOS 7.X 云服务器数据盘扩容教程,必须确认服务器符合以下要求,否则请勿操作。
参谋带个长
2024/07/02
1.6K0
记录下Windows2008服务器转Linux无法加载数据盘的情况
上周网站突然出现问题,打开之后显示Fast CGI错误(代码0x80070005),采用宝塔windows控制面板,然后就抓紧时间拍错,百度,搜狗等等,能用的都用了,按照教程各种设置,还是无效,时间紧迫,赶紧把官网转移到我的服务器,保证网站正常可以访问。接下来的时候就是开始折腾。
李洋博客
2021/06/15
5.7K0
linux恢复硬盘初始状态,初始化Linux数据盘(fdisk)[通俗易懂]
初始化Linux数据盘(fdisk)TkV南京数据恢复-西数科技: 硬盘/手机/SSD数据恢复专家. 025-83608636 18913825606
全栈程序员站长
2022/09/02
6.7K0
Linux磁盘-格式化&挂载
作者介绍:简历上没有一个精通的运维工程师。希望大家多多关注作者,下面的思维导图也是预计更新的内容和当前进度(不定时更新)。
运维小路
2024/11/01
1.6K0
Linux磁盘-格式化&挂载
推荐阅读
相关推荐
【玩转云服务器】Linux(CentOS)挂载数据盘(小于2T)
更多 >
交个朋友
加入前端学习入门群
前端基础系统教学 经验分享避坑指南
加入前端工作实战群
前端工程化实践 组件库开发经验分享
加入前端趋势交流群
追踪前端新趋势 交流学习心得
换一批
领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档