本文将通过用于向队列发送消息和从队列接收消息的示例应用程序说明如何在 Linux 上着手安装和配置 WebSphere MQ,以及如何为 MQ 环境开发 Java 应用程序。

引言

本文的目标是让您轻松实现 Linux® 上的 IBM® WebSphere® MQ 入门。由于大部分 Linux 服务器并没有图形用户界面,因此本文将说明如何使用命令行工具在 Linux 上安装和配置 WebSphere MQ。本文将说明如何使用 WebSphere MQ Java API 创建两个示例 Java™ 应用程序:MQSend(用于向队列发送消息)和 MQGet(用于从队列接收消息)。

先决条件

  • WebSphere MQ V6 安装包。
  • 一台或两台安装了 Linux 的计算机。本文使用两台安装了 Suse Linux Enterprise Server V9 的计算机,不过也可以在一台计算机上完成所有工作。
  • Linux 管理技能。
  • Java 开发方面的经验将有所帮助,但并非必须的,因为我们提供了经过预编译的 Java 示例应用程序供下载和在命令行使用。

WebSphere MQ

WebSphere MQ 提供了连接层和应用程序的可靠集成,为 SOA 提供了所需的基础。WebSphere MQ 的主要特色功能包括:

有保证的消息交付
基于可靠队列的消息传递,可确保消息不会丢失或重复。
基于标准的开发
使用 Java Message Service (JMS) API 和 Message Queue Interface (MQI)。
端到端安全
使用安全套接字层(Secure Sockets Layer,SSL)进行身份验证、消息完整性检查和数据加密。
Web 服务支持
用于保证 Web 服务传输和可靠性的简单对象访问协议(Simple Object Access Protocol,SOAP)。
异步处理
对应用程序进行分离,以支持进行独立于时间的处理。
多平台支持
支持 80 种以上的配置。

有关 WebSphere MQ 的更多信息,请参见本文结尾的参考资料。

安装 WebSphere MQ

安装 WebSphere MQ 的过程非常简单——直接将安装包释放到目录中即可(本文使用 root 主目录下的 mq_install)。可以安装 RPM 安装包中的所有内容,但本文仅需要这部分东西。以下是 WebSphere MQ V6 中包括的包和目录:

IBMJava2-SDK-1.4.2-0.0.i386.rpm
MQSeriesClient-6.0.0-0.i386.rpm
MQSeriesConfig-6.0.0-0.i386.rpm
MQSeriesFTA-6.0.0-0.i386.rpm
MQSeriesIES30-6.0.0-0.i386.rpm
MQSeriesJava-6.0.0-0.i386.rpm
MQSeriesKeyMan-6.0.0-0.i386.rpm
MQSeriesMan-6.0.0-0.i386.rpm
MQSeriesMsg_Zh_CN-6.0.0-0.i386.rpm
MQSeriesMsg_Zh_TW-6.0.0-0.i386.rpm
MQSeriesMsg_de-6.0.0-0.i386.rpm
MQSeriesMsg_es-6.0.0-0.i386.rpm
MQSeriesMsg_fr-6.0.0-0.i386.rpm
MQSeriesMsg_it-6.0.0-0.i386.rpm
MQSeriesMsg_ja-6.0.0-0.i386.rpm
MQSeriesMsg_ko-6.0.0-0.i386.rpm
MQSeriesMsg_pt-6.0.0-0.i386.rpm
MQSeriesRuntime-6.0.0-0.i386.rpm
MQSeriesSDK-6.0.0-0.i386.rpm
MQSeriesSamples-6.0.0-0.i386.rpm
MQSeriesServer-6.0.0-0.i386.rpm
MQSeriesTXClient-6.0.0-0.i386.rpm
PreReqs
READMEs
copyright
gsk7bas-7.0-3.15.i386.rpm
lap
licenses

下面是安装步骤:

  1. 设置 Linux 服务器。本文使用主机名 WMQ1WMQ2WMQ1 的 IP 地址为 192.168.28.71,WMQ2 的 IP 地址为 192.168.28.72。
  2. 安装 WebSphere MQ 前,必须执行 ./mqlicense.sh,以阅读和接受许可证。
  3. 安装所需的 MQ 包及 WebSphere MQ Java 和 IBM Java SDK 包,以便为 WebSphere MQ 开发 Java 客户机:
    wmq1:~/mq_install # rpm -ivh IBMJava2-SDK-1.4.2-0.0.i386.rpm
    wmq1:~/mq_install # rpm -ivh MQSeriesRuntime-6.0.0-0.i386.rpm
    wmq1:~/mq_install # rpm -ivh MQSeriesServer-6.0.0-0.i386.rpm
    wmq1:~/mq_install # rpm -ivh MQSeriesJava-6.0.0-0.i386.rpm
    

WebSphere MQ 现在已经完成安装,并有用于进行配置的名为 mqm 的用户和组。缺省情况下,WebSphere MQ 安装在 /opt/mqm 中,队列和其他配置信息位于用户 mqm 的主目录中。Java SDK 安装在 /opt/IBMJava2-142 中,Java 解释程序位于 /opt/IBMJava2-142/bin 中。

下一步是进行配置。本文为两台计算机使用了具有本地和远程队列的单个队列管理器,用于测试示例应用程序。

配置 WebSphere MQ

WebSphere MQ 术语和定义

队列管理器
提供队列服务和 API 及用于管理队列的管理功能的系统管理程序。
队列
消息所发送到的命名目的地。
本地队列
位于队列管理器本地的队列。
远程队列
驻留在其他队列管理器(可能位于其他主机上)的队列。
传输队列
以远程队列为目标的临时消息队列。
通道
队列管理器之间的通信路径。
侦听器
从客户机或其他队列管理器接受网络请求。
命令服务器
验证命令并将有效命令发送到命令处理器(后者随后执行命令)。

配置过程包括以下几个步骤:

  • 创建队列管理器。
  • 启动队列管理器。
  • 创建队列和通道。
  • 启动命令服务器、侦听器和通道。

两台 WebSphere MQ 计算机都需要执行这些步骤。下面的部分将仅说明如何在 WMQ1 上进行配置,但在 WMQ2 上也需要进行这些步骤。

创建并启动队列管理器

使用 root 登录到 WMQ1,然后键入 su - mqm,以更改到用户 mqm。使用以下命令为 WMQ1 计算机创建队列管理器:

mqm@wmq1:~/ # crtmqm WMQ1QM

使用以下命令启动队列管理器。

mqm@wmq1:~/ # strmqm WMQ1QM

创建队列和通道

使用命令行工具配置 WebSphere MQ。以下给出了 WMQ1 的配置脚本。此脚本定义本地队列、远程队列、传输队列、发送方通道和接收方通道。将以下脚本保存为 WMQ1QM.conf:

DEFINE QLOCAL ('WMQ1InputQ') +
REPLACE
DEFINE QLOCAL ('WMQ2QMXmitQ') +
DESCR('Transmission Queue to WMQ2QM') +
USAGE(XMITQ) +
TRIGGER +
TRIGTYPE(FIRST) +
TRIGDPTH(1) +
TRIGDATA('WMQ1QM.WMQ2QM') +
INITQ('SYSTEM.CHANNEL.INITQ') +
REPLACE
DEFINE QREMOTE ('WMQ1OutputQ') +
XMITQ('WMQ2QMXmitQ') +
RNAME('WMQ2InputQ') +
RQMNAME('WMQ2QM') +
REPLACE
DEFINE CHANNEL ('WMQ1QM.WMQ2QM') CHLTYPE(SDR) +
TRPTYPE(TCP) +
CONNAME('192.168.28.72(1414)') +
XMITQ('WMQ2QMXmitQ') +
REPLACE
DEFINE CHANNEL ('WMQ2QM.WMQ1QM') CHLTYPE(RCVR) +
TRPTYPE(TCP) +
REPLACE
DEFINE CHANNEL ('SYSTEM.ADMIN.SVRCONN') CHLTYPE(SVRCONN) +
TRPTYPE(TCP) +
DESCR(' ') +
HBINT(300) +
MAXMSGL(4194304) +
MCAUSER('MUSR_MQADMIN') +
RCVDATA(' ') +
RCVEXIT(' ') +
SCYDATA(' ') +
SCYEXIT(' ') +
SENDDATA(' ') +
SENDEXIT(' ') +
REPLACE

上面的配置脚本可作为其他 WebSphere MQ 安装的模版使用。只需要更改粗体部分的名称,即可在其他 WebSphere MQ 安装中设置队列和通道。此配置脚本中包含大量条目——有关它们的更多信息,请参见 WebSphere MQ 信息中心。

使用以下命令创建队列和通道,以配置 WebSphere MQ:

mqm@wmq1:~/ # runmqsc WMQ1QM < WMQ1QM.conf > qcreate.log

runmqsc 命令用于发出 WebSphere MQ 命令。在本例中,这些命令从 WMQ1QM.conf 文件读取,而输出被定向到 qcreate.log。打开 qcreate.log,验证其中不存在语法错误,全部有效命令均得到了处理。

启动服务

需要启动命令服务器、侦听器和通道,然后就可以进行示例应用程序的部署和测试工作了。

mqm@wmq1:~/ # strmqcsv WMQ1QM &
mqm@wmq1:~/ # runmqlsr -m WMQ1QM -t TCP &

验证队列管理器和侦听器在两台计算机上运行,然后启动通道:

mqm@wmq1:~/ # runmqchl -m WMQ1QM -c WMQ1QM.WMQ2QM &
mqm@wmq1:~/ # runmqchl -m WMQ1QM -c WMQ2QM.WMQ1QM &

现在已经安装了 WebSphere MQ,并进行了配置,已准备好可以进行测试了。下面一部分将给出两个基于 Java 的应用程序的源代码,分别用于向队列发送消息和从队列接收消息。

示例应用程序

用于将消息放入队列中 (MQSend) 和从队列获取消息 (MQGet) 的示例 Java 应用程序可使用前面部分中定义的队列。这些应用程序支持 String 消息,旨在用于测试和作为说明如何从 Java 应用程序使用 WebSphere MQ 的示例。可以从脚本使用应用程序,包括各种类型的应用程序。MQSend 和 MQGet 都从 MQConnector 类进行扩展,该类可提供 WebSphere MQ 连接、初始化 WebSphere MQ、打开和关闭队列,向队列发送消息及从队列接收消息。

MQConnector

MQConnector 是用于进行发送和获取操作的超类。该类处理打开连接和发送及获取消息的工作。将使用属性文件对其进行配置,需要在属性文件中指定主机地址、队列管理器名称和队列名称:

queue.manager=WMQ1QM
queue.manager.host=192.168.28.71
queue.name=WMQ1OutputQ

以下是 MQConnector 源代码:

package mqconn;
import java.io.File;
import java.io.FileInputStream;
import java.io.IOException;
import java.util.Properties;
import com.ibm.mq.MQC;
import com.ibm.mq.MQEnvironment;
import com.ibm.mq.MQException;
import com.ibm.mq.MQGetMessageOptions;
import com.ibm.mq.MQMessage;
import com.ibm.mq.MQPutMessageOptions;
import com.ibm.mq.MQQueue;
import com.ibm.mq.MQQueueManager;
public class MQConnector
{
protected String qManager = ""; // define name of queue manager
protected String qManagerHost = "";
protected String queuName = ""; // define name of queue
protected MQQueue mqQueue;
protected MQQueueManager qMgr;
public static boolean DEBUG = true;
public MQConnector()
{
}
public void initMq()
{
try
{
FileInputStream fis = new FileInputStream(new File("mqconnect.properties"));
Properties props = new Properties();
props.load(fis);
fis.close();
qManager = props.getProperty("queue.manager");
qManagerHost = props.getProperty("queue.manager.host");
queuName = props.getProperty("queue.name");
// Create a connection to the queue manager
MQEnvironment.channel = "SYSTEM.DEF.SVRCONN";
MQEnvironment.hostname = qManagerHost;
debug("Connecting to QueueManager " + qManager + " on " + qManagerHost);
qMgr = new MQQueueManager(qManager);
}
catch (Exception e)
{
e.printStackTrace();
}
}
public void openQueue() throws MQException
{
// Set up the options on the queue we wish to open...
// Note. All WebSphere MQ Options are prefixed with MQC in Java.
int openOptions = MQC.MQOO_INPUT_AS_Q_DEF | MQC.MQOO_OUTPUT;
// Now specify the queue that we wish to open,
// and the open options...
debug("Opening queue: " + queuName);
try
{
mqQueue = qMgr.accessQueue(queuName, openOptions);
}
catch(MQException mqe)
{
//check if MQ reason code 2045
//means that opened queu is remote and it can not be opened as
//input queue
//try to open as output only
if(mqe.reasonCode==2045)
{
openOptions = MQC.MQOO_OUTPUT;
mqQueue = qMgr.accessQueue(queuName, openOptions);
}
}
}
public void putMessageToQueue(String msg) throws MQException
{
try
{
debug("Sending message: " + msg);
MQPutMessageOptions pmo = new MQPutMessageOptions();
MQMessage mqMsg = new MQMessage();
mqMsg.write(msg.getBytes());
// put the message on the queue
mqQueue.put(mqMsg, pmo);
}
catch (IOException e)
{
e.printStackTrace();
}
}
public String getMessageFromQueue() throws MQException
{
try
{
MQMessage mqMsg = new MQMessage();
MQGetMessageOptions gmo = new MQGetMessageOptions();
// Get a message from the queue
mqQueue.get(mqMsg,gmo);
//Extract the message data
int len=mqMsg.getDataLength();
byte[] message = new byte[len];
mqMsg.readFully(message,0,len);
return new String(message);
}
catch(MQException mqe)
{
int reason=mqe.reasonCode;
if(reason==2033)//no messages
{
return null;
}
else
{
throw mqe;
}
}
catch (IOException e)
{
e.printStackTrace();
return null;
}
}
public void closeQueue() throws MQException
{
debug("Closing queue and disconnecting QueueManager...");
// Close the queue...
mqQueue.close();
// Disconnect from the queue manager
qMgr.disconnect();
}
protected boolean hasArg(String arg, String[] args)
{
for(int i=0;i<args.length;i++)
{
if(args[i].equals(arg))
{
return true;
}
}
return false;
}
public void debug(Object msg)
{
if (DEBUG)
{
System.out.println(msg);
}
}
}

该类向其他应用程序提供 WebSphere MQ 功能。还可以在自己的应用程序中将 MQConnector 作为其他类的超类或实用类使用。以下方法为 Java 应用程序提供消息传递功能:

initMQ()
读取属性并创建队列管理器对象。
openQueue()
打开属性文件中指定的队列。
closeQueue()
关闭已打开的队列。
disconnectMq()
断开队列管理器。
putMessageToQueue(String)
将字符串消息放置到指定的队列。
getMessageFromQueue()
从指定的队列读取字符串消息。

MQSend

MQSend(如下所示)将使用 MQConnector 类,是用于向队列发送消息的命令行程序。消息作为命令行参数指定,可以使用其将文件内容作为消息发送:

package mqconn;
import java.io.BufferedReader;
import java.io.FileReader;
import com.ibm.mq.MQException;
public class MQSend extends MQConnector
{
public MQSend()
{
}
public void send(String[] args) throws MQException
{
boolean argsAreFiles = hasArg("-f", args);
initMq();
openQueue();
for (int i = 0; i < args.length; i++)
{
if (args[i].equals("-f"))
continue;
if (!argsAreFiles)
{
putMessageToQueue(args[i]);
}
else
{
try
{
// send file contents as message
BufferedReader br = new BufferedReader(new FileReader(args[i]));
StringBuffer msg = new StringBuffer();
for (String line = br.readLine(); line != null; line = br.readLine())
{
msg.append(line);
msg.append('/n');
}
br.close();
putMessageToQueue(msg.toString());
}
catch (Exception e)
{
System.out.println("Error while processing file " + args[i] + ": "
+ e.toString());
}
}
System.out.println("Message sent.");
}
closeQueue();
disconnectMq();
}
public static void main(String[] args)
{
MQSend mqsend = new MQSend();
MQConnector.DEBUG = false;
try
{
if (args == null || args.length == 0)
{
System.out.println("Usage: " + mqsend.getClass().getName()
+ " [-f] <file name | message> [<file name | message> ...]");
System.exit(0);
}
mqsend.send(args);
}
catch (Exception e)
{
System.out.println(e.toString());
System.out.println("Usage: " + mqsend.getClass().getName()
+ " [-f] <file name | message> [<file name | message> ...]");
}
}
}

MQSend 使用 MQConnector 提供消息传递,实际的 MQSend 程序功能非常简单。它有两种操作模式:

  • 将每个命令行参数作为独立消息传递。
  • 使用 -f 选项发送文件内容。在本例中,每个命令行参数都是文件名。

MQGet

MQGet 类(如下所示)非常简单——从指定的队列检索消息,并将其写入到标准输出。可以通过使用重定向将消息存储在文件中。

package mqconn;
import com.ibm.mq.MQException;
public class MQGet extends MQConnector
{
public MQGet()
{
}
public String getMessages(String[] args) throws MQException
{
String message=getMessageFromQueue();
return message;
}
public static void main(String[] args)
{
MQGet mqget = new MQGet();
MQConnector.DEBUG=false;
try
{
mqget.initMq();
mqget.openQueue();
String msg=mqget.getMessages(args);
if(msg!=null)
{
System.out.println(msg);
}
mqget.closeQueue();
mqget.disconnectMq();
}
catch (Exception e)
{
e.printStackTrace();
System.out.println("Usage: "+mqget.getClass().getName()+" ");
}
}
}

MQGet 使用 mqconnect.properties 文件中指定的队列管理器和队列。下一部分将给出一些可供进行测试的示例用例。

示例用例

以下是一些用例,均使用 WMQ1 作为发送方,WMQ2 作为接收方,说明了如何使用 MQSend 和 MQGet 应用程序。

准备工作

在使用示例前,您需要进行一些准备工作,如设置属性和编写一些 Helper 脚本等。为 WMQ1 中的 MQSend 应用程序使用以下属性:

queue.manager=WMQ1QM
queue.manager.host=127.0.0.1
queue.name=WMQ1OutputQ

为 WMQ2 中的 MQGet 应用程序使用以下属性:

queue.manager=WMQ2QM
queue.manager.host=127.0.0.1
queue.name=WMQ2InputQ

为了节约键入的时间,以下提供了用于进行发送和接收的两个脚本。

/opt/IBMJava2-142/bin/java -cp .:com.ibm.mq.jar mqconn.MQSend "$@"
/opt/IBMJava2-142/bin/java -cp .:com.ibm.mq.jar mqconn.MQGet "$@"

使用 chmod 755 mqsendchmod 755 mqget 将这些脚本转换为可执行文件。本文中的所有类和文件都位于 /var/mqm/bin 目录中,其中 /var/mqm 是 mqm 用户的主目录。

命令

第一个示例命令将消息发送到上面指定的队列。下面的示例清单给出了实际的命令,另外还给出了命令的输出。

mqm@wmq1:~/bin> ./mqsend "This is test message"
MQJE001: Completion Code 2, Reason 2045
Message sent.

MQJE001 是预期出现的内容。Reason 2045 表示在本例中无法将要打开的队列作为输入队列打开,因为此队列是远程队列。MQJE001 由 WebSphere MQ 类输出到标准错误。如果不希望看到这些错误消息,请将标准错误重新定向到 /dev/null ./mqsend "This is test message" 2> /dev/null。若要了解原因代码的含义,请使用 mqrc 2045

在 WMQ2 上,使用 mqget 命令接收消息:

mqm@wmq2:~/bin> ./mqget
This is test message

如果再次执行 mqget,会看到预期的 MQJE001 消息。mqrc 2033 中的 2033 表示“MQRC_NO_MSG_AVAILABLE”。检索消息并将其从队列删除。以下代码说明了如何发送多个消息:

mqm@wmq1:~/bin> ./mqsend "This is test message" This is another message
MQJE001: Completion Code 2, Reason 2045
Message sent.
Message sent.
Message sent.
Message sent.
Message sent.

接收消息与上面所示的 mqget 命令相同。以下代码说明了如何接收多个消息:

mqm@wmq2:~/bin> ./mqget
This is test message
mqm@wmq2:~/bin> ./mqget
This
mqm@wmq2:~/bin> ./mqget
is
mqm@wmq2:~/bin> ./mqget
another
mqm@wmq2:~/bin> ./mqget
message
mqm@wmq2:~/bin> ./mqget
MQJE001: Completion Code 2, Reason 2033

下一个示例将发送所有 Java 文件的内容:

mqm@wmq1:~/bin> ls -1 mqconn/*.java | awk '{print "mqsend -f "$1""}' | sh 2> /dev/null
Message sent.
Message sent.
Message sent.

下一个示例读取消息并将其保存到文件中:

mqm@wmq2:~/bin> ./mqget > msg1.txt

mqget 命令的输出被定向到 msg1.txt。

结束语

本文说明了 Linux 上的 WebSphere MQ 使用入门知识。只需要进行一些安装和配置步骤,就能让 WebSphere MQ 正常运行,而这些步骤正是了解 WebSphere MQ 的更多信息的良好起点。文中提供的示例应用程序说明了可以如何方便地获取对 WebSphere MQ 及消息传递功能的访问。示例应用程序还可作为开发自定义应用程序的不错借鉴。


回页首

下载

描述 名字 大小 下载方法
Sample code mqsamples.zip 332 KB HTTP

本文转自 http://www.ibm.com/developerworks/cn/websphere/library/techarticles/0705_salkosuo/0705_salkosuo.html#resources

Linux上的WebSphere MQ开发快速入门相关推荐

  1. linux查看websphereMQ版本,Linux上安装WebSphere MQ 7.1

    Linux上安装WebSphere MQ 7.1 1. 解压缩 1. tar -zxvf WMQ_7.1.0.3_TRIAL_LNX_X86_64_ML.tar.gz 2. license accep ...

  2. IM开发快速入门(一):什么是IM系统?

    本文在编写时参考了博客作者"鹿呦呦"和在线课程"即时消息技术剖析与实战"的相关资料,一并表示感谢. 1.系列文章引言 IM系统看似简单(没错,很多土老板认为开发 ...

  3. 海思HI35xx平台软件开发快速入门之H264解码实例

    前言 H264视频编码技术诞生于2003年,至今已有十余载,技术相当成熟,它的优势在于有高的视频的压缩率,利用帧间和帧内预测(Estimation).变换(Transform)和反变换.量化(Quan ...

  4. HealthKit开发快速入门教程之HealthKit框架体系创建健康AppID

    HealthKit开发快速入门教程之HealthKit框架体系创建健康AppID HealthKit开发准备工作 在开发一款HealthKit应用程序时,首先需要讲解HealthKit中有哪些类,在i ...

  5. HealthKit开发快速入门教程之HealthKit开发概述简介

    HealthKit开发快速入门教程之HealthKit开发概述简介 2014年6月2日召开的年度开发者大会上,苹果发布了一款新的移动应用平台,可以收集和分析用户的健康数据.该移动应用平台被命名为&qu ...

  6. 游戏控制杆OUYA游戏开发快速入门教程

    游戏控制杆OUYA游戏开发快速入门教程 1.2.2  游戏控制杆 游戏控制杆各个角度的视图,如图1-4所示,它的硬件规格是本文选自OUYA游戏开发快速入门教程大学霸: 图1-4  游戏控制杆各个角度的 ...

  7. Transform组件C#游戏开发快速入门

    orm组件C#游戏开发快速入门大学霸 Transform组件C#游戏开发快速入门 组件(Component)可以看作是一类属性的总称.而属性是指游戏对象上一切可设置.调节的选项,如图2-8所示.本文选 ...

  8. OUYA游戏开发快速入门教程1.2OUYA的硬件规格

    OUYA游戏开发快速入门教程1.2OUYA的硬件规格 从官网上购买回来的OUYA产品,包含游戏主机.游戏控制杆.说明书.电源线.HDMI线.电源线和电池,如图1-2所示.本节就来简要介绍下,游戏主机和 ...

  9. OUYA游戏开发快速入门教程第1章了解OUYA及其设备

    OUYA游戏开发快速入门教程第1章了解OUYA及其设备 OUYA是基于Andorid系统的游戏主机.围绕OUYA游戏机,已经形成一个完整的生态圈.在国外,OUYA已经成为知名的游戏平台.本章会站在玩家 ...

最新文章

  1. freebsd系统/: write failed, filesystem is full问题解决办法
  2. 几种和生成网络相似的纠缠网络(接近人脑)
  3. docker 私有仓库与Harbor
  4. 【Hive】一次被分区条件和笛卡尔积制裁的经历
  5. 共模电压和差模电压-(定义及测量)
  6. Sail(CodeForces - 298B )
  7. 【整理】Spring 常用注解!千万不要错过!
  8. 删掉SQL Server登录时登录名下拉列表框中的选项
  9. T-SQL 之 执行顺序
  10. 02331数据结构 散列表
  11. jvm学习笔记(1)——java虚拟机内存区域
  12. VB循环For的一点启示
  13. java 定时程序扫描表_Java扫描程序类
  14. SpringBoot properties和yml的区别
  15. editplus使用php,EditPlus配置PHP调试环境详细图文介绍
  16. videos player.php_基于vue-video-player自定义播放器的方法
  17. 《使用Nsis打包安装程序》
  18. 【Windows Mobile】Win10 停留在加载界面无法进入主界面
  19. CDR服装设计-旗袍款式图
  20. 23计算机考研人第一周反思总结

热门文章

  1. java笔记--关于线程同步(7种同步方式)
  2. 【剑指offer】不使用新变量,交换两个变量的值,C++实现
  3. Vue 进入/离开动画
  4. oracle学习(二)pl/sql基础
  5. sql server 2008学习9 编写脚本和批处理
  6. Redhat Linux网卡配置与绑定
  7. 网管日志-06.07.21
  8. JavaScript实现省市联动
  9. Django REST framework快速入门
  10. flink on yarn部分源码解析 (FLIP-6 new mode)