node.js 详细学习笔记(还未学习完版的笔记)。

本教程深入讲解Node.js的基础知识,包括命令行操作、环境变量设置、进程与线程概念、Node.js特性及其版本管理。此外,还介绍了如何通过不同方式执行js文件,模块化编程,CommonJS规范的应用,以及npm包管理器的使用方法,包括依赖管理和镜像服务器的配置。

主要参考书: nodejs中文网

http://nodejs.cn/api/

 

命令行的操作(DOS)

 

table键自动补全

 

dir:列出当前目录下所有文件。

 

cd 目录名 进入到指定目录

md 目录名 创建一个文件夹

rd 目录名 删除一个文件夹

 

.     表示当前目录

..    表示上一级目录

 

环境变量:(windows系统中变量)(不管是在哪个盘,都可以用)

但是改完了环境变量,必须得重启cmd窗口。

 

当我们在命令行窗口打开一个文件,或者调用一个文件时,系统会首先在当前目录下寻找文件程序,如果找到了则直接打开,如果没有找到则会依次到环境变量path的路径中寻找,直到找到为止,如果没找到则报错。

 

所以我们可以将一些经常需要访问的程序和文件的路径添加到path中,这样我们就以在任意位置来访问这些文件了。

 

 

进程和线程:

 

进程:

任务管理器->进程->会看到各种各样的软件。

负责为程序运行提供必备环境。

进程相当于工厂中的车间。

 

线程:

计算机中最小计算单位,负责执行进程中的程序

单线程:js是单线程

多线程:

 

 

Node.js(瑞恩达尔)

Js最初是为了写高性能web服务器(最开始叫web.js)

一个能够在服务器端运行js的js运行环境。

(之前学的都是在浏览器运行的)

可以通过js,写应用。用的google的V8引擎

事件驱动、非阻塞、异步I/O模型

高并发问题

客户端请求服务器,服务器和数据库之间输入输出操作,服务器相应客户端。

所有项目开发最后的瓶颈都是输入输出操作(服务器和数据库之间的。)

面临问题。

传统服务器都是多线程(对硬盘要求高)的,每进来一个请求,就给一个线程。

i/o会阻塞

 

node.js奇数版本为测试版本,偶数版本为稳定版本。

淘宝会在客户端和服务器里面加一层服务器(node服务器,专门用来渲染页面,处理高并发请求。)可以增加服务器的数量,变成分布式。

 

 

方式一:

怎样通过找目录方式使用node执行js文件。

 

方式二:

快捷方式:

 

 

会直接进入到图上的那么一个界面。

嗯,完成。

 

 

软件的terminal即为终端==命令行。

vs code直接调试js代码即可。

结果就会被运行出来的。

 

ECMAScript缺陷:

1.没有模块系统,但是有模块化(比如说jquery,引入jquery相关的文件。)

模块化:方便维护&&可以复用

主机电脑就是模块化的。

2.标准库较少(目前的这些库很多都是其他非标准的程序员自行开发的)

3.没有标准接口。

4.缺乏管理系统。

 

CommonJS规范

他的提出是为了弥补当前JS没有标准的缺陷。

但是对模块的定义十分简单。

模块引用

模块定义

模块标识。

因此一个js就是一个模块

 

模块化:

在node中,一个js文件就是一个模块。

在node中,而每一个js文件中的js代码都是独立运行在一个函数中。

而不是全局作用域,所以一个模块中的变量和函数在其它模块中无法访问。

 

函数

在node中,通过require()函数来引入外部的模块

require()可以传递一个文件的路径作为参数,node将会自动根据该路径来引入外部模块。

这里路径,如果使用相对路径,必须以.或者..开头。

 

使用require()引入模块以后,该函数会返回一个对象,这个对象代表的是引入的模块。

 

我们使用require()引入外部模块时,使用的就是模块标识,比如说,那个路径就是模块标识,我们可以通过指定的标识去找到模块。

模块分为两大类:

   核心模块:(kernel module)

          由node引擎提供的模块

          核心模块的标识就是——模块的名字

(比如说我们想用node里面直接给我们提供的文件模块,怎么引入?

var fs=require(“fs”);//不用写路径了,直接写名就可以,因为这是核心给我们提供的。

( 看是否被引入了

       console.log(fs);

   文件模块:

          由用户自己创建的模块

          文件模块的标识就是文件的路径(绝对路径,相对路径)

                 相对路径使用.或..开头。

 

02.module.js

console.log(“我是02.module.js”);   //屏幕显示。

var x=10;       //这个变量对于其他模块都是封闭的

var y=20;       //若想暴露其内容:

//向外部暴露属性或方法,我们可以通过 exports 来向外部暴露变量和方法。

//只需要将需要暴露给外部的变量或方法设置为exports的属性即可。

exports.z=”我是02.module.js中的z”;

exports.fn=function(){

      

}

                                                                                        

03.module.js:

require(“./02.module.js”);

//想要使用02.module.js里面的变量,方法如下:

var md= require(“./02.module.js”);

console.log(md);

                      

小作业

math.js

/*    定义一个模块math

在该模块中提供两个方法

       add(a,b);        //求两个数的和

       mul(a,b);        //求两个数的积    */

exports.add=function(a,b){

return a+b;};

exports.mul=function(a,b){

return a*b};

quote.js:

var math=required(“.math”);

console.log(math.add(123,456));

 

 

                                                                                     

 

 

验证var a=10;是不是全局变量?

又怎样将一个变量变成全局变量(去掉var这个符号,即可)

证明04.module.js里面的代码确实是在函数里面运行的(找到一个东西只有函数里面有。

如果想看当前执行的是哪个函数呢?

console.log(arguments)  //arguments是封装函数的实参的)。

arguments.callee(arguments的属性callee保存的是当前执行的函数对象。)

如果想看当前执行的函数的内部结构呢?

       console.log(arguments.callee + ”” );

       //之前如果直接调,它会把对象打印出来,而现在如果加一个字符串,进行拼串,拼串就会调用toString(),把这个函数的结构给打出来。

 

/*

       在node中有一个全局对象global,它的作用和网页中window类似。

              在全局中创建的变量都会作为global的属性保存

              在全局中创建的函数都会作为global的方法保存。

 

       当node在执行模块中的代码时,它会首先在代码的最顶部,添加如下代码:

              function(exports ,require ,module , _filename ,_dirname){ }

       实际上模块中的代码都是包装在一个函数中执行的,并且在函数执行时,同时传递进了五个实参。

       exports

              该对象用来将变量或函数暴露到外部

      require

              函数,用来引入外部模块

       module

              module代表的是当前模块本身。

              exports就是module的属性

              既可以使用exports到处,也可以使用module.exports导出

           console.log(exports);  ==  console.log(module.exports);

       _filename

              当前模块的完整路径。

              console.log(_filename);

       _dirname

              当前模块所在文件夹的完整路径。

 

*/

04.module.js:

var a=10;

console.log(global.a);

console.log(arguments);      //全局里面是不可能有arguments的

console.log(arguments.callee);

console.log(arguments.length);

//运行这个js文件,系统会报a undefined。(但是当去掉了var,就会显示10了。)

 

                                                                               

 

helloModule.js:

exports.name=”孙悟空”;

exports.age=18;

exports.sayName=function(){

       console.log(“我是孙悟空~~~”);

}

加强版本(注:去掉了module.这个就不能这么使用了,原因:(要区分是改变量还是改对象。)

eports和module.exports

       通过exports只能使用.的方式来向外暴露内部变量

              export.xxx=xxx

      而module.

):

module.exports = {

       name:”猪八戒”,

       age:28,

       sayName:function(){

              console.log(“我是猪八戒”);

}

}

var obj = {};

 

05.module.js:

var hello = require(“./helloModule”);

console.log(hello.name);

console.log(hello.age);

hello.sayName();

 

 

内存分为栈内存和堆内存。

new Object();        //使用的是堆内存

 

                                                                               

 

commonJS的包规范由包结构和包描述文件两个部分组成。

包即模块的集合。

包结构

       用于组织包中的各种文件。

包描述文件

       描述包的相关信息,以供外部读取分析。

 

包其实是压缩文件,解压以后还原为目录。

package.json        描述文件(这个必须得有)

bin         可执行二进制文件

lib          js代码

doc        文档

test        单元测试

 

任何的json文件里都不能写注释。

                                                                               

 

 

NPM(node package manager)node包管理器

NPM帮助其完成了第三方模块的发布,安装和依赖。

可以进入cmd界面打开npm

 

npm指令:

npm -v                           查看版本  

npm version                      查看所有模块的版本(更详细)

npm                              帮助说明

npm search 包名                  搜索模块包

npm install / i 包名             在当前目录安装包

npm remove / r 包名              删除包

npm install 包名                全局模式安装包

 

npm install / i –save           安装包并添加到依赖中 **********

 

npm install                     下载当前项目所依赖的包(它会自动根据

我们的配置依赖信息,去npm下载这些包。就不用自己一个个找,在网上下载了node项目,拿到不要直接运行,先跑到根目录install一下。)

 

npm install 包名 -g              全局安装包(全局安装的包一般都是一些

工具)

 

npm config set registry 地址    设置镜像源

 

npm install 包名 --registry=地址   从镜像源安装。

 

首先你需要一个安装npm相关包的目录,

新建了一个文件夹。

然后进入到这个文件夹下,打开cmd命令

输入npm init (init的作用就是创建一个package.json)

注意npm命名时:不允许使用大写字母。

description:描述,不写也行。

entry point:入口的点。我们写一个程序和模块,会有很多js文件,那么问题来了,哪个js文件是你程序的入口。npm默认的是index.js文件是我们程序的入口。

剩下的选项一路回车即可。

然后回到这个文件夹。

就会发现自动给我们生成了一个

然后我们打开这个package.json,会发现里面是根据刚才给的那些提示那么写的。

然后我们再执行npm install math

就会发现我们这个路径文件夹下的东西有这些:

注意:node里的所有模块都会装到node.modules里面。

如果你想第一时间了解某个模块,就看当前模块下面的package.json

然后再在这个文件夹下面创建一个:index.js

如果我们想在index.js里面引入math模块怎么办?

index.js:

var math = require("math");

console.log(math);

console.log(math.add(123,456));

 

 

                                                                               

 

npm i math

在想要安装这个包的路径下执行此操作。

会出现一个modules包,点开包里面会继续有一个modules包

但是这种方法并不是依赖绑定。

一般来说,我们讲究的是依赖绑定。

因此我们先

npm r math

把这个包删除(它会自己去modules这个包下找到math这个包,递归的查找,如果modules包里只有这个math包,那么它会直接也罢modules这个包给我们也删除)

 

可以看到modules->math都被删除掉了。

现在开始,用依赖关系进行创建。

依赖关系引入math这个包最大的不同就是,在引入math这个包的同时,我们的package.json的内容会被注入math包的相关信息。

 

 

打开目录下面的package.json会发现里面

有了一个dependencies依赖。

依赖里面是一个对象——math,后面跟着的是它的版本。

所以—save的特点就是,安装的同时,把这个包设置成了你的依赖。

 

这样做有一个好处,就是你假如把modules这个包删掉了。

那么这个时候去打开你的index.js是会出错的。

但是有依赖关系,--save的优点就出来了。这个时候可以在cmd中执行

npm install       //后面什么都不用跟。

我们再打开这个文件夹,会发现它已经自动的把东西给我们下载好了。

 

 

                                                                                

 

 

npm i express –save

express这个包还挺大的。

npm是外国的,服务器在国外,npm,美国服务器进行下载包,会下很长时间,有一些情况不稳定。

所以有镜像服务器。

通过镜像服务器去下载,连接中国的镜像服务器,防止被墙。

所以,怎么去用镜像服务器?

 

百度搜索:淘宝NPM镜像

同步频率每十分钟与官方服务同步。

那个网站上就有使用说明。

 

cnpm命令:(指令就是一模一样的,把npm换成cnpm)

npm install -g cnpm --registry=https://registry.npm.taobao.org

-g全局安装,装了一个cnpm,并且把后面那一坨设置为它的地址。

但是第一次很慢。

用这个的好处是,如果想连接原来的服务器还用npm,如果说原来的服务器连接慢,那么就用cnpm。

 

 

执行这条命令。

 

成功安装。

现在我们再来执行:

cnpm i express --save

 

 

但是会发现其实cnpm这种下载的目录跟npm下载的目录不是那么一样:

 

原因是:毕竟不是从官方原版下载下来的,所以这些文件名都跟官方的那些文件名不太一样,前面加了下划线,后面加了版本之类的东西,做了一些区分,然后里面通过快捷方式对这些文件进行了关联。

 

如下图:

这是为了什么呢?

这是为了避免如果我们又有官方版本,又有淘宝版本的话,cnpm版本不会覆盖官方版本。

所以这个就不用管了。

 

 

                                                                               

 

我们在这个目录下创建一个06.npm.js文件:

D:\Users\windymoon\Desktop\npm

通过npm下载的包都放到node_modules文件夹中。

注意:我们通过npm下载的包,直接通过包名引入即可。

        形如:var math=require("math")

调试如下图:

 

注意: node在使用模块名字来引入模块时,

它会首先在当前目录的node_modules中寻找是否含有该模块,

如果有则直接使用,如果没有则去上一级目录的node_modules中寻找。

递归,如果有则直接使用,如果没有则再去上一级目录寻找,直到找到位置。

直到找到磁盘的根目录,如果依然没有,则报错。

 

 

                                                                               

 

/*

Buffer (缓冲区)

    buffer的结构和数组很像,操作的方法也和数组类似。

    js数组的性能比其他的语言差。

    数组中不能存储二进制的文件,而buffer就是专门用来存储二进制数据的。

    比传统数组性能要好点。

 

    使用Buffer不需要引入模块,直接使用即可。

 

buffer中存储的都是二进制数据,但是在显示时,都是以16禁止的形式显示的。

buffer中每一个元素的范围是从00-ff 0-255 00000000-111111111

 

计算机中一个0,或者一个1,成为1位(bit)

8bit=1byte(字节)

1024byte=1kb

……

最小传输单位是字节

 

一个汉字三个字节。

 

console.log(buf.length);//占用内存的大小

console.log(str.length);//字符串的长度

 

buffer所有构造函数都是不推荐使用的。

 

buffer的大小一旦确定,则不能修改。buffer实际上是对底层内存的实际操作。buffer的内存空间必定是连续的。

 

Buffer.from(str) 将一个字符串转换为buffer

Buffer.alloc(size) 创建一个指定大小的buffer

Byffer.allocUnsafe(size) 创建一个指定大小的Buffer,但是可能包含敏感数据。

buf.toString() 将缓冲区中的数据转换为字符串。

*/

 

 

 

buf.length与str.length的区别(一个汉字三个字节):

 

创建一个指定大小的buffer:

但是下面这种(构造函数)方法,不推荐使用。

 

 

nodejs的中文官网:nodejs.cn

只要数字在控制台输出一定是十进制,否则的话,没有统一标准,区分不了。

但是只要不是数字,那么就可以想办法了。

比如:调用toString(16)这个方法,把那个变量转换为16进制进行输出:

像这样:就输出了aa

 

for循环遍历buffer数组

 

方法:

Buffer.allocUnsafe(size) 创建一个指定大小的buffer,但是buffer中可能含有敏感数据(buffer是直接对内存进行操作的,之前的alloc方法,它会清空内存里面的数据,清理完了,之后的呈现给我们进行操作,而allocUnsafe不会,有可能那段内存里面有值,但它不会清空,因此可能不会全是000000……)。

这个只分配空间,而不修改数据。

alloc分配空间的同时,会修改数据。

 

 

下面的代码就会发现,输出结果并不是000000……

 

 

                                                                               

 

fs(文件系统)

文件系统——就是通过Node来操作系统中的文件。

服务器的本质就是将本地的文件发送给远程的客户端。

使用文件系统,需要先引入fs模块,fs是核心模块,直接引入即可。

 

fs模块中所有的操作都有两种形式可供选择(成对出现):同步与异步。

sync:同步方法

不带sync的:异步方法

同步文件系统:会组设程序的执行,除非操作完毕,否则不会向下执行。

异步文件系统:不会阻塞程序的执行,而是在操作完成时,通过回调函数将结果返回。(都有callback函数)

 

同步文件的写入:

    手动操作的步骤:

  1. 打开文件

fs.openSync(path, flags[, mode])

    -path 要打开文件的路径。(相对路径)

    -flags 打开文件要做的操作的类型。

        r 只读的

        w 可写的

    -mode 设置文件的操作权限,一般不传

返回值:

    该方法会返回一个文件的描述符作为结果,我们可以通过该描述符来对文件进行各种操作。

  1. 像文件中写入内容

[fs] fs.writeSync(fd, string[, position[, encoding]])

              -fd 文件的描述符,需要传递要写入的文件的描述符

              -string 要写入的内容

              -position 写入的起始位置

              -encoding 写入的编码,默认utf-8

 

  1. 保存并关闭文件。

因为服务器并不会停止,如果你打开了文件不关闭,就会一直占用内存空间。

[fs] fs.closeSync(fd)

    -fd 要关闭的文件的描述符

 

 

02.fs.js:

 

var fs=require("fs");

var fd = fs.openSync("hello.txt", "w");

console.log(fd);

console.log(fs);

 

运行结果如图:

 

在这里我发现了有一个叫做launch.json的文件,里面的代码那个index.js就是它要执行的文件项目,所以我把02.js文件里面的内容复制粘贴到了index.js文件里面,才运行正确了。

准备向文件里写入内容,js内代码如下:

var fs=require("fs");

var fd = fs.openSync("hello.txt", "w");

console.log(fd);

 

fs.writeSync(fd ,"今天天气真不错~~~");

 

 

因为我的这个软件,有两种方法:一种是启动调试(这种的话,向文件里面写入内容是不成功的。),直到我用了后面一种,在不调试的情况下启动,才成功写入了数据。

 

这样下来,打开hello.txt,会发现内容已经成功写入。

 

关闭文件:

var fs=require("fs");

var fd = fs.openSync("hello.txt", "w");

console.log(fd);

fs.writeSync(fd ,"今天天气真不错~~~");

fs.closeSync(fd);

 

另:

var fs=require("fs");

var fd = fs.openSync("hello.txt", "w");

console.log(fd);

fs.writeSync(fd ,"今天天气真不错~~~",20);

fs.closeSync(fd);

 

 

 

异步方法不可能有返回值,只要有返回值,那肯定就是同步的。

因为不然就必须得等它返回结果,之后的才能被执行,所以这种就形成不了异步了。

异步文件的写入:

    手动操作的步骤:

  1. 打开文件

[fs] fs.open(path, flags[, mode], callback)

    -path 要打开文件的路径。(相对路径)

    -flags 打开文件要做的操作的类型。

        r 只读的

        w 可写的

    -mode 设置文件的操作权限,一般不传

    -callback must be a function

返回值:

    该方法会返回一个文件的描述符作为结果,我们可以通过该描述符来对文件进行各种操作。

  1. 像文件中写入内容

[fs] fs.writeSync(fd, string[, position[, encoding]])

              -fd 文件的描述符,需要传递要写入的文件的描述符

              -string 要写入的内容

              -position 写入的起始位置

              -encoding 写入的编码,默认utf-8

 

  1. 保存并关闭文件。

因为服务器并不会停止,如果你打开了文件不关闭,就会一直占用内存空间。

[fs] fs.closeSync(fd)

    -fd 要关闭的文件的描述符

 

index.js

var fs = require("fs");

//打开文件

fs.open(hello.txt","w",function(){})

 

 

3:44s

 

                                                                              

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值