初识Node.js之Node与java作为后台服务器的对比
> 文章原创于公众号:程序猿周先森。本平台不定时更新,喜欢我的文章,欢迎关注我的微信公众号。

想想好久没有更新文章了,最近去了新公司,又拾起了被我抛下许久的后端了,不过因为公司的需求,后端采用node.js,最近一直在学习Node.js,随着逐渐深入的了解,发现真的node能越来越变得热门是有其存在的道理的。可能有人会说,java作为后端语言一直隐隐有龙头老大的姿势,为何我们还要去学node呢?Node.js究竟是什么?它是新的语言还是新的框架,是新的工具抑或只是一个简单的JavaScript文件?
**运行时环境**
我们众所周知Java具有一个称作JRE的运行时环境来使得java程序能够顺利运行。JRE有一个称为JVM的虚拟机。JVM有许多组件,如垃圾回收器(GC),即时(JIT)编译器,解释器,类装载器,线程管理器,异常处理器,用于在不同时间执行不同的任务。JRE还有一系列的库来帮助运行时的Java程序。
我们为什么要突然牵扯到JRE运行时环境呢,其实正是为了与node作比较,Node不是一种语言,也不是框架,更不是工具,它是运行JavaScript应用程序的运行时环境。Node.js有一个称为JavaScript Virtual Machine的虚拟机。它为基于JavaScript的应用程序生成机器代码,以便在不同的平台上启用它。这个虚拟机就是Google的V8引擎,也有主要组件,如JIT和GC,分别用于执行任务,运行时编译,和内存管理。
**发展潜力**
判断Java和node的发展潜力可能要从其背后的生态社区和支持库上切入,然而以Java为核心的传统体系自然比不上node这样的新势力,简而言之,Java成熟而庞大,node迅捷而活跃。java其功能性和实用性自然不必多说,但是java包含了大量的样品代码,扰乱了程序猿所想表达的意图,就不如java三大框架之一的spring,程序猿在使用spring的时候servlet,数据持久,以及构成系统的底层的东西,spring框架已经封装好会帮助你处理这一切,我们只需要专注于写业务层代码就足以。但是在Spring中,子系统一个接一个,哪怕你犯最微小的错误,它都会用让你崩溃的异常来惩罚你。可能紧接着你就会看到巨大的异常信息。里面包含着一个一个你根本不知道的封装好的方法,Spring做了许多工作来实现代码的功能。这种级别的抽象显然需要大量的逻辑,长长的异常信息不一定是坏事,它指出了一个症状:这需要多少内存和性能上的额外开销?spring是怎么执行的?框架需要解析方法名、猜测程序员的意图、构建类似于抽象语法树的东西、生成SQL等等。这些事情的额外开销有多大?所以说使用java掩盖复杂性并不会因此简单化,只会让系统更复杂。java严格的类型检查使得Java帮你避免许多类型的bug,因为不好的代码无法通过编译。Java的强类型的缺点就是太多样板代码。程序员要不断进行类型转换,程序员要花掉更多时间写精确的代码,使用更多的样板代码,以图早期发现错误并改正。
而Node.js恰恰相反。线程会导致更复杂化的系统。所以Node.js采用轻量级,单线程的系统,利用了js的匿名函数进行异步回调,你只需要简单的使用匿名函数,也就是闭包。不需要搜索正确的抽象接口,只需要写下业务代码,没有任何冗余。这就是使用Node.js的最大好处,不过异步回调自然也出现一个急需解决的问题:回调陷阱。
在Node.js中,我们不断嵌套回调函数的同时,很容易就陷入回调函数的陷阱中,每层嵌套都会让代码更复杂,使得错误处理和结果处理更困难。一个相关的问题就是js语言不会帮助程序员恰当地表达异步执行。其实有些库会使用Promise来简化异步操作,但是看起来我们把问题简单化了,但是事实上代码层面更复杂化了,Promise用了许多样板代码,掩盖了程序员的真实意图。后来Node.js支持ES5与ES6,可以采用async/await函数重写回调函数。还是同样的异步结构,但使用了正常的循环结构来书写。错误和结果处理的位置也很自然,代码更易于理解,更容易编写,而且也可以很容易地理解程序员的意图。回调陷阱并不是用掩盖复杂性的方式解决的。相反,语言和范式的改变解决了回调陷阱的问题,同时还解决了过多样板代码的问题。有了async函数,代码就更漂亮了。简单化的解决方法,将Node.js的缺点转化为了优点。
但是JavaScript的类型很松散。而且在你书写代码的时候不会进行报错,许多类型不需要定义,通常也不需要用类型转换。因此代码更清晰易读,但存在漏掉编码错误的风险,只有在编译的时候才会去检查你语法以及逻辑是否存在问题,所以在Node.js中,为了更好的调试BUG,node支持将程序分成不同的模块,因为有模块的存在,将错误发生的范围缩小到某个范围内,使得Node.js模块更容易测试。
**包管理**
java最重要的问题之一就是没有统一的包管理系统,可能有人会和我说Maven。但是无论是用途、易用性还是功能上,Maven与Node.js的包管理系统相比简直是天壤之别。npm 是 Node.js 官方提供的包管理工具,他已经成了 Node.js 包的标准发布平台,用于 Node.js 包的发布、传播、依赖控制。npm 提供了命令行工具,使你可以方便地下载、安装、升级、删除包,也可以让你作为开发者发布并维护包。最好的地方是npm代码库不仅供Node.js使用,也可以让前端工程师使用。所有的前端JavaScript库都以npm包的形式存在。许多前端工具如Webpack都是用Node.js编写的。
**性能**
java使用HotSpot这个超级虚拟机,它采用了多字节编译策略。它会检测经常执行的代码,一段代码执行次数越多,就会应用越多的优化。因此HotSpot性能相对来说更快。Node底层选择用c++和v8引擎来实现的,node.js的事件驱动机制,这意味着要面对大规模的http请求,node.js是凭借事件驱动来完成的,性能部分是不用担心的,并且很出色。而且,由于V8引擎的改进,Node.js的每次发布都会带来巨大的性能提升。
虽然Node对高并发应用有着极高的性能,但是Node.js也有着自己的缺点:
* Node不适合CPU密集型应用,因为CPU密集型应用如果有长时间的运算,不如大循环,将会导致CPU时间片不能释放,使得后续的IO操作全部暂停。
* 而且Node只支持单核CPU,不能充分利用CPU资源
* 可靠性低,一旦代码某个环节崩溃,将会导致整个系统都崩溃,原因就在于Node是使用单进程。
* Node的开源组件库质量参差不齐,更新快,而且不向下兼容。
其实Node.js作为后端能实现几乎所有应用,只是我们选择的时候考虑更多的是项目场景是不是适合用NodeJS。
**欢迎关注我个人公众号:程序猿周先森**

初识Node.js之Node与java作为后台服务器的对比的更多相关文章
- [翻译] 比较 Node.js,Python,Java,C# 和 Go 的 AWS Lambda 性能
[翻译] 比较 Node.js,Python,Java,C# 和 Go 的 AWS Lambda 性能 原文: Comparing AWS Lambda performance of Node.js, ...
- node.js 初学(一)—— http fs 服务器/文件/post get
node.js 初学 —— http fs 服务器/文件/post get 这个世界,从来不会给失败者颁奖! 了解 node.js (开源) node.js 是用来做后台开发的,但是现在大部分前端人员 ...
- 一起来学node.js吧 node school简介
node.js这几年火爆的简直丧心病狂,去lagou.com查查node.js的职位,那叫一个多. 要说火爆到什么程度,竟然有一个网站专门去教大家学习node.js, Node School. 进去逛 ...
- 用 Node.js 实现的最简单的 HTTP 服务器
用 Node.js 实现的最简单的 HTTP 服务器 //app.js var http = require('http'); http.createServer(function(req, res) ...
- atitit.js javascript 调用c# java php后台语言api html5交互的原理与总结p97
atitit.js javascript 调用c# java php后台语言api html5交互的原理与总结p97 1. 实现html5化界面的要解决的策略1 1.1. Js交互1 1.2. 动态参 ...
- 【Node.js】Node.js的调试
目录结构: contents structure [-] 使用console.log() 使用Chrome DevTools 使用Visual Studio Code 与JavaScript运行在浏览 ...
- 极简 Node.js 入门 - Node.js 是什么、性能有优势?
极简 Node.js 入门系列教程:https://www.yuque.com/sunluyong/node 本文更佳阅读体验:https://www.yuque.com/sunluyong/node ...
- 关于安装完Node.js 出现node is not dedined 问题
今天想来接触下Node.js 神奇 怀着揣揣的心 从官网下载了windows 的64位mis版本 几个下一步就顺利安装完毕了 接着跟着新手教程走 不懂教程里的 苹果shell 是什么 反正就是检 ...
- Node.js入门-Node.js 介绍
Node.js 是什么 Node.js 不是一种独立的语言,与 PHP,Python 等"既是语言优势平台"不同,它也不是一个 JavaScrip 框架,不同于 CakePHP,D ...
随机推荐
- 基于UDP的socket tcp和udp的区别(小白进击篇)
目录 16.基于udp协议的socket通信 为什么udp不会有粘包现象 DGRAM datagram#数据报文 发送sento (发送的信息,发送给的地址) 接收revefrom 客户端 服务端 t ...
- Redis之对象篇——Redis对象系统简介
Redis之对象篇--Redis对象系统简介 前言 之前几篇文章,简单介绍 Redis用到的所有主要数据结构,简单动态字符串(SDS).双端链表.字典.压缩列表.整数集合.跳跃表. 图解Red ...
- SQL Server检索存储过程的结果集
目的:检索过滤执行存储过程的结果集 如下介绍两个常用的方法,但是都需要申明表结构:不知道是否有更简便的方法,如有更好的方法,请不吝赐教. 以系统存储过程sp_who2为例: 方法1:使用临时表 --1 ...
- 消息中间件——RabbitMQ(七)高级特性全在这里!(上)
前言 前面我们介绍了RabbitMQ的安装.各大消息中间件的对比.AMQP核心概念.管控台的使用.快速入门RabbitMQ.本章将介绍RabbitMQ的高级特性.分两篇(上/下)进行介绍. 消息如何保 ...
- HuffmanTree
/* 例如,对于数列{pi}={5, 3, 8, 2, 9},Huffman树的构造过程如下: 1. 找到{5, 3, 8, 2, 9}中最小的两个数,分别是2和3,从{pi}中删除它们并将和5加入, ...
- 以太坊智能合约[ERC20]发币记录
以太坊被称为区块链2.0,就是因为以太坊在应用层提供了虚拟机,使得开发者可以基于它自定义逻辑,通常被称为智能合约,合约中的公共接口可以作为区块链中的普通交易执行.本文就智能合约发代币流程作一完整介绍( ...
- 微信小程序 es6-promise.js封装请求 处理异步进程
下载es6-promise.js置于根目录下的libs文件夹下: 在根目录utils文件夹下新建httpsPromisify.js,即定义封装请求的方法 var Promise = require(' ...
- Mysql系列 - 第3天:管理员必备技能(必须掌握)
这是mysql系列第3篇文章. 环境:mysql5.7.25,cmd命令中进行演示. 在玩mysql的过程中,经常遇到有很多朋友在云上面玩mysql的时候,说我创建了一个用户为什么不能登录?为什么没有 ...
- C#开发学习人工智能的第一步
前言 作为一个软件开发者,我们除了要学会复制,黏贴,还要学会调用API和优秀的开源类库. 也许,有人说C#做不了人工智能,如果你相信了,那只能说明你的思想还是狭隘的. 做不了人工智能的不是C#这种语言 ...
- JSONP跨域的script标签请求为什么不受同源策略的限制?
在复习跨域的时候,复习到了JSONP跨域,大家都知道JSONP跨域是通过动态创建script标签,然后通过其src属性进行跨域请求的,前端需要一个数据处理的回调函数,而服务端需要配合执行回调函数,放入 ...