node.js入門學習(一)環境安裝,REPL,fs模塊,path模塊,http模塊


錄:
一、node.js介紹
二、node.js有哪些特點
三、下載安裝node.js,配置環境變量
四、node.js開發網站和傳統PHP等開發網站的區別
五、REPL介紹
六、helloworld程序
七、案例:輸出一個三角形
八、fs寫入文件和讀取文件
九、__dirname和__filename獲取正在執行的js文件的路徑
十、使用path模塊進行路徑拼接
十一、通過http模塊構建一個簡單的http服務程序
十二、Buffer

一、node.js介紹    <--返回目錄

  1.1、node.js是什么

    官網首頁總結:Node.js® 是一個基於 Chrome V8 引擎 的 JavaScript 運行時。

    1)node.js是一個開發平台,就像java開發平台、.net開發平台、PHP開發平台、Apple開發平台一樣。
      - 什么是開發平台:有對應的編程語言、有語言運行時、有能實現特定功能的API(SDK Software Development Kit)
    2)node.js平台使用的編程語言是JavaScript。
    3)node.js平台是基於Chrome V8 JavaScript 引擎構建。


  1.2、node.js可以做什么

    1)基於node.js可以開發控制台程序(命令行程序、CLI程序)、桌面應用程序(GUI,要借助node-webkit、electron等框架實現)、web應用程序(網站)
    2)PHP開發技術棧:LAMP - Linux Apache MySQL PHP
    3)node.js全棧開發技術棧:MEAN- MongoDB Express Angular Node.js

二、node.js有哪些特點    <--返回目錄

  1)事件驅動:當事件被觸發,執行傳遞過去的回調函數
  2)非阻塞I/O模型:當執行I/O操作時,不會阻塞線程
  3)單線程
  4)擁有世界最大的開源庫生態系統-npm

   node.js在處理高並發、I/O密集場景性能優勢明顯。

    - CPU密集:壓縮、解壓、加密、解密

    - I/O密集:文件操作、網絡操作、數據庫操作

 

  web常見場景:靜態資源讀取、數據庫操作、渲染頁面。

  node.js的單線程:單線程只是針對主進程,I/O操作系統底層多線程調度。

 

三、下載安裝node.js,配置環境變量    <--返回目錄

  node.js官方網站:https://nodejs.org/
       中文網: http://nodejs.cn/
       中文社區:https://cnodejs.org/

  下載win 64為安裝包:node-v10.16.0-x64.msi,雙擊安裝

  

 

  為了在任何目錄下都可以使用node和npm命令,將這兩個命令添加到環境變量path。我安裝node時默認就添加到了環境變量。

  

 

四、node.js開發網站和傳統PHP等開發網站的區別    <--返回目錄

  1)傳統php、java、asp.net開發web程序需要web容器
  2)node.js本身就是web服務器
          - 接收用戶請求后,根據不同的請求直接做對應處理
          - 把處理后的結果返回給瀏覽器

 

五、REPL介紹    <--返回目錄
  1)REPL全稱Read Eval Print Loop交互式解釋器
          - R 讀取,讀取用戶輸入,解析輸入js數據結構並儲存在內存中
          - E 執行,執行輸入的數據結構
          - P 打印,輸出結果
          - L 循環,循環操作以上步驟直到用戶兩次按下Ctrl+c按鈕退出
        
  2)在REPL中編寫程序,類似於瀏覽器開發人員工具中的控制台功能。

  3)直接在控制台輸入node命令,進入REPL環境

  4)按兩次Ctrl+c 或者輸入 .exit ,退出REPL界面

  

 

六、helloworld程序    <--返回目錄

  新建一個helloworld.js

var m = 10;
var n = 20;
function add(x, y) {
    return x + y;
}
console.log(m + "和"+ n + "相加,等於" + add(m,n));


  在包含helloworld.js文件的目錄下,shift+右鍵,在此處打開命令窗口;輸入命令 node hel(tab補全),控制台會打印結果

   

 

七、案例:輸出一個三角形    <--返回目錄

  process模塊是全局模塊,直接使用;

for(var i = 0; i <10; i++) {
    for(var j = 0;j <=i; j++) {
        process.stdout.write("* ");
    }
    console.log();
}

 

八、fs寫入文件和讀取文件    <--返回目錄
  process模塊是全局模塊,直接使用;fs不是全局模塊,要用require加載

  fs寫入文件:

// 加載文件操作fs模塊
var fs = require("fs");
// 文件寫入
// fs.writeFile('文件路徑','數據','選項',function(){});
fs.writeFile('./a.txt','hello world', 'utf-8', (err) => {
    // 如果err===null,表示寫入文件成功
    // 只要err不是null,就表示寫入文件失敗
    if (err) {
        throw err;
        console.log("數據寫入失敗: " + err);
    } else {
        console.log("數據寫入成功");
    }
});

 

  fs文件追加內容:

fs.appendFile('./test.txt', 'bbbb', 'utf8', err => {
    console.log('done')
})

 

   fs讀取文件:

// 加載文件操作fs模塊
var fs = require("fs");
// fs.ReadFile('文件路徑','選項',function(){});
// 文件路徑'a.txt'是相對於執行node命令的路徑 
fs.readFile('./a.txt','utf-8',(err,data) => {  
    if (err) {
        throw err;
        console.log("數據讀取失敗");
    } else {
        console.log(data);
    }
});

    fs.stat() 判斷是文件還是文件夾

fs.stat('./a.js', (err, stats) => {
    if (err) {
        console.log('文件不存在'); // 一般可以用來判斷文件是否存在 return;
    };

    console.log(stats.isFile());
    console.log(stats.isDirectory());

    console.log(stats);
});

   fs.rename() 重命名

fs.rename('./text', 'test.txt', err => {
    if(err) throw err;

    console.log('done!');
});

  fs.unlink() 刪除

fs.unlink('./test.txt', err => {});

  fs.readdir() 讀取文件夾內容

fs.readdir('../', (err, files) => {
    if (err) throw err;

    console.log(files);
})

  fs.mkdir() 創建目錄

fs.mkdir('test', err => {});

  fs.watch() 監視文件或文件夾的變化

fs.watch('./', {recursive: true}, (eventType, filename) => {
    console.log(eventType, filename);
});

 

  fs同步的方法

const fs = require("fs");

// 同步的讀取
var data = fs.readFileSync("./test.txt", 'utf8'); 

console.log("文件讀取完成, data: ", data);

//同步的寫入
fs.writeFileSync("./test.txt", '很好', 'utf8');

//同步的追加
fs.appendFileSync("./test.txt", '呵呵', 'utf8');

 

九、__dirname和__filename獲取正在執行的js文件的路徑    <--返回目錄

  前面的程序都是在hello.js所在目錄執行node ./hello.js命令。如果進到c盤,執行node D:\hello.js命令,結果:

  

 

   __dirname表示當前正在執行的js文件的所在目錄;__filename表示當前正在執行的js文件的完整路徑

//fs讀取文件
// 加載文件操作fs模塊
var fs = require("fs");
// fs.writeFile('文件路徑','選項',function(){});
// fs.readFile(__dirname+'\\a.txt','utf-8',(err,data) => {
fs.readFile(__dirname+'/a.txt','utf-8',(err,data) => {
    if (err) {
        throw err;
        console.log("數據讀取失敗");
    } else {
        console.log(data);
    }
});

 

   所以,"./hello.js"中./是相對於執行node命令的路徑,而不是相對於當前js文件的路徑。

 

   __dirname和__filename不是全局的,但是為什么使用的時候不需要通過require引入:

(
    function ("__dirname", "__filename") {
        //fs讀取文件
        // 加載文件操作fs模塊
        var fs = require("fs");
        // fs.writeFile('文件路徑','選項',function(){});
        // fs.readFile(__dirname+'\\a.txt','utf-8',(err,data) => {
        fs.readFile(__dirname+'/a.txt','utf-8',(err,data) => {
            if (err) {
                throw err;
                console.log("數據讀取失敗");
            } else {
                console.log(data);
            }
        });
    }
)("當前正在執行的js文件的所在目錄","當前正在執行的js文件的完整路徑");

   總結:__dirname、__filename總是返回文件的絕對路徑;

        process.cwd()總是返回執行node命令所在文件夾; 

     require()方法總是相對當前文件;

        pahth.resolve('./')是執行node命令所在文件夾

 

十、使用path模塊進行路徑拼接    <--返回目錄

  path會根據系統拼接成對應的路徑,windows下格式是 \a\b\c

var path = require('path');
var str = path.join('/foo','bar','baz/asdf');
console.log(path);
process.stdout.write(str); // \foo\bar\baz\asdf
const path = require('path')

// normalize: 將路徑解析成標准的格式
console.log(path.normalize('/usr/local//bin')) // \usr\local\bin
console.log(path.normalize('/usr/local/../bin')) // \usr\\bin

// resolve: 將相對路徑解析成絕對路徑
console.log(path.resolve('./')) // D:\當前文件所在目錄名

// basename: 取文件名, dirname: 文件夾, extname: 擴展名
const pathName1 = path.basename('c:/a/b.js')
console.log(pathName1) // b.js
const pathName2 = path.basename('c:\\a\\b.js')
console.log(pathName2) // b.js

const filePath = '/usr/local/bin/a.txt'
console.log(path.basename(filePath)) // a.txt
console.log(path.dirname(filePath)) // /usr/local/bin
console.log(path.extname(filePath)) // .txt

console.log('='.repeat(50))
// parse format
const parseResult = path.parse(filePath)
console.log(parseResult) // {root:'/', dir:'/usr/local/bin', base:'a.txt', ext:'.txt', name:'a'}
// parseResult對象中dir和base優先級高,即有這個兩個屬性,其他屬性值忽略掉。因為有dir和base屬性就可以完全拼接出完整的文件名
console.log(path.format(parseResult)) // /usr/local/bin\a.txt
const path = require('path')
// sep delimiter win32 posix
console.log('當前系統下sep: ', path.sep)
console.log('win sep:', path.win32.sep)
console.log('posix sep', path.posix.sep)

console.log('PATH: ', process.env.path)
console.log('當前系統下delimiter: ', path.delimiter) // delimiter是PATH的分隔符
console.log('win delimiter: ', path.win32.delimiter)
console.log('posix delimiter: ', path.posix.delimiter)

 

十一、通過http模塊構建一個簡單的http服務程序    <--返回目錄

  第一步:在d:/hello.js寫代碼:

// 加載http模塊
var http = require("http");

// 創建一個http服務對象
var server = http.createServer();

// 監聽用戶的請求
server.on('request', function(req,res) {
    res.setHeader('content-type','text/html;charset=utf-8');
    res.write('<h1>hello 您好!</h1>');
    res.end();//結束響應
});

// 開啟服務
server.listen('8080', function() {
    console.log('服務器已經啟動。');
});

  第二步:cmd窗口輸入node D:\hello.js運行程序

  第三步:瀏覽器輸入http://localhost:8080。

 

十二、Buffer    <--返回目錄

  Buffer用於處理二進制數據流,類似數組,但是Buffer大小固定。

  構造Buffer

console.log(Buffer.alloc(5)) // 默認0填充
console.log(Buffer.alloc(5, 1)) //0x1填充
console.log(Buffer.allocUnsafe(5)) // 保持原有數據
console.log(Buffer.from([1, 2, 3]))
console.log(Buffer.from('test')) // 默認utf-8編碼
console.log(Buffer.from('test', 'base64'))

  Buffer的byteLength()、isBuffer()、concat()方法

/* 
Buffer.byteLength()
Buffer.isBuffer()
Buffer.concat()
*/
console.log(Buffer.byteLength('test')) // 4
console.log(Buffer.byteLength('測試')) // 6, utf-8編碼

console.log(Buffer.isBuffer({})) // false
console.log(Buffer.isBuffer(Buffer.from([1, 2, 3]))) // true

const buf1 = Buffer.from('hello')
const buf2 = Buffer.from('世界')
const buf3 = Buffer.from('!')
const buf = Buffer.concat([buf1, buf2])
console.log(buf.toString()) // hello世界!

  buf.length、buf.toString([encoding])、buf.fill(value[, start, end])

const buf = Buffer.allocUnsafe(10)
buf[2] = 0xff
console.log(buf.length)
console.log(buf)

buf.fill(0xff)
console.log(buf)

const buf2 = Buffer.from('hello world')
console.log(buf2.toString())
console.log(buf2.toString('base64'))

  buf.equals()、buf.indexOf()

const buf1 = Buffer.from('test')
const buf2 = Buffer.from('test')
console.log(buf1.equals(buf2)) // 比較內容是否相同,true

console.log(buf1.indexOf('te')) // 0
console.log(buf1.indexOf('abc')) // 找不到,返回-1

---


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM