netty java_Netty框架学习及第一个Netty应用

编辑推荐:

本文来自于csdn,文章主要介绍了Netty的基础,有什么特点,其构成部分是什么,以及相关的应用。

1.什么是Netty?

Netty是一个利用Java的高级网络的能力,隐藏其背后的复杂性而提供一个易于使用的API的客户端/服务器框架。Netty提供高性能和可扩展性,让你可以自由地专注于你真正感兴趣的东西。

2.发展历史:

网络发展初期,花费很多时间学习socket的复杂、寻址等,在C socket库上进行编码,并需要在不同的操作系统上做不同的处理。

Java早期版本(1995-2002)介绍了足够的面向对象的糖衣来隐藏一些复杂性,但实现客户端-服务器协议仍需要大量的样板代码和大量的监视才能确保他们是对的。早期的API只能通过原生的socket库来支持所谓的?blocking功能。

JAVA NIO,非阻塞API,阻塞性I/O一般工作流程如图示:

91097d8791de3884227e0228e0065616.png

这种方式在连接数比较少的时候还是可以接受的,当并发连接超过10000时,开销会明显增加。此外,每一个县城都有一个默认的堆栈内存分配了128K和1M之间的空间。考虑到整体的内存和操作系统需要处理更多的并发连接资源,所以这似乎不是一个理想的解决方案。

SELECTOR,实现Java的无阻塞I/O实现的关键,工作流程如下:

ce9ea52b5656e305fdbeeee59b1cf6ed.png

最终由Selector决定哪一组注册的socket准备执行I/O。通过通知,一个县城可以同时处理多个并发连接(一个Selector通常由一个线程处理,但具体实施可以使用多个线程)因此,每次读或写操作执行能立即检查完成。该模型可以用较少的线程处理更多连接,这意味着在内存和上下文切换上话费更少的开销,当没有I/O处理时,线程可以被重定向到其他任务上。

我们可以世界使用JavaAPI构建的NIO构建应用程序,但这样做正确和安全无法保证,实现可靠和可扩展的event-processing(事件处理器)来处理和调度数据并保证尽可能有效,不过这是一个繁琐和容易出错的任务,而这些,就交给了Netty。

3.Netty特点

设计:

针对多种传输类型的同一接口-阻塞和非阻塞;

简单但更强大的线程模型;

真正的无连接的数据报套接字支持;

连接逻辑支持复用。

易用性:

大量的javadoc和代码实例;

出了在JDK1.6+额外的限制。

性能:

比核心Java API更好的吞吐量,较低的延时;

资源消耗更少,这个得益于于共享池和重用;

减少内存拷贝。

健壮性:

消除由于慢、快、活重载连接产生的OutOfMemoryError;

消除经常发现在NIO在告诉网络中的应用中的不公平的读/写比。

安全:

完整的SSL/TLS和StartTLS的支持;

运行在受限的环境例如Applet活OSGI。

社区:

发布的更早和更频繁;

社区驱动。

4.异步和事件驱动

非阻塞I/O不会强迫我们等待操作的完成。

5.构成部分

Channel:NIO基本结构,代表一个用于连接到实体如硬件设备、文件、网络套接字或程序组件,能否执行一个或多个不同的I/O操作的开放连接。

Callback:回调方法,提供给另一种方法作为引用,时间接口可由ChannelHandler的实现来处理。

Future:提供了另一种通知应用操作已经完成的方式,这个对象作为一个一步操作结果的占位符,他将在将来的某个时候完成并提交结果。Netty提供自己的实现,ChannelFuture,用于执行异步操作时使用。每个Netty的outbound

I/O操作都会返回一个ChannelFuture,这样就不会阻塞,这便是Netty所谓的“自底向上的异步和事件驱动”。相关实现的步骤如下:

1.异步连接到远程对等节点,调用立即返回并提供ChannelFuture;

2.操作完成后通知注册一个ChannelFutureListener;

3.当operationComplete()调用时检查操作的撞他;

4.如果成功就创建一个ByteBuf来保存数据;

5.异步发送数据到远程,再次返回ChannelFuture;

6.如果有一个错误则抛出Throwable,描述错误原因。

Event和Handler:Netty使用不同的事件来通知我们更改的状态或操作的状态,这使我们能够根据发声的事件触发适当的行为。这些行为可能包括:日志、数据转换、流控制、应用程序逻辑,由于Netty是一个网络框架,事件很清晰的跟入栈或出出站数据流相关,因为一些事件可能触发的传入的数据或状态的变化包括:活动或非活动连接、数据的读取、用户事件、错误,出站事件是由于在未来操作将触发的一个动作,这些包括:打开或关闭一个连接到远程、写或冲刷数据到socket。每个事件都可以分配给用户实现处理程序类的方法,这些范例可直接转换为应用程序构建块,如图:

336359d0a06d861818973d87d18fad68.png

Netty的ChannelHandler是各种处理程序的基本抽象,每个处理器实例就是一个回调,用于执行各种事件的响应。

6.整合

FUTURE,CALLBACK和HANDLER

Netty的异步编程模型是建立在future和callback的概念上的,所有这些元素的协同为自己的设计提供了强大的力量。拦截操作和转换入站或出站数据只需要提供回调或者利用future操作返回的,这是用的链操作简单、高校,促进编写可重用的、通用的代码。一个Netty的设计的主要目标是促进“关注点分离”,即我们的业务逻辑从网络基础设施应用程序中分离。

SELECTOR,EVENT和EVENT LOOP

Netty通过触发事件从应用程序中抽象出Selector,从而避免手写调度代码,EventLoop分配给每个Channel来处理所有的事件,包括:注册感兴趣的事件、调度事件到ChannelHandler、安排进一步行动。该EventLoop本身由只有一个线程驱动,它给一个Channel处理所有的I/O事件,并且在EventLoop的生命周期内不会改变,这个简单而强大的线程模型消除你可能对你的ChannelHandler同步的任何关注,这样你就可以专注提供正确的回调逻辑来执行。?

7.第一个Netty应用

7.1Netty客户端/服务器总览,Echo client/server

58c403df22b86b57ede32f151e659ba4.png

图中显示了连接到服务器的多个并发客户端,理论上,客户端可以支持的连接数只受限于使用的JDK版本中的制约。

echo(回声)客户端和服务器之间的交互是很简单的:客户端启动后,建立一个连接发送一个或多个消息到服务器,其中每相呼应消息返回给客户端。这个应用程序并不是非常有用,但这项工作是为了更好的理解请求--相应交互本身,这是一个基本的模式的客户端/服务器系统。

7.2 写一个echo服务器

Netty实现的echo服务器需要下面内容:

一个服务器handler:该组件实现了服务器的业务逻辑,决定了连接创建后和接受到信息后如何处理;

Bootstrapping:这个配置服务器的启动代码,最少需要设置服务器绑定的端口,用来监听连接请求。

通过ChannelHandler来实现服务器的逻辑,使用ChannelHandler的方式体现了“关注点分离”的设计原则,并简化业务逻辑的迭代开发的要求,处理程序很简单,每一个方法都可以覆盖到“hook(钩子)”在活动周期适当的点。牢记两点:

ChannelHandler是给不同类型的事件调用;

应用程序实现或扩展ChannelHandler挂接到事件生命周期和提供自定义应用逻辑。

Echo server将接受到的数据拷贝发送给客户端,因此,我们需要实现ChannelInboundHandler接口,用于自定义处理入站事件的方法,当前应用简单,只需继承ChannelInboundHandlerAdapter就行了,该类提供了默认ChannelInboundHandler的实现,所以只需覆盖以下方法:

channelRead()--每个信息入站都会调用,覆盖该方法是因为我们需要处理所有接收到的数据;

channelReadComplete()--通知处理器最后的channelRead()是当前处理中的最后一条消息调用;

exceptionCaught()-读操作时捕获到异常时调用,覆盖该方法使我们能够应对任何Throwable的子类

? 型,在这种情况下我们记录、并关闭所有可能处在未知状态的连接,它通常是难以从连接错误中恢复,所以干脆关闭远程连接,当然,也有可能的情况是可以从错误中恢复的,所以可以用一个更复杂的措施来尝试识别和处理这样的情况。每个Channel都有一个关联的ChannelPipeline,它代表了ChannelHandler实例的链,适配器处理的实现知识讲一个处理方法调用转发到链中的下一个处理器,因此,如果一个Netty应用程序不覆盖exceptionCaught,那么这些错误最终将到达ChannelPipeline,并且结束警告将被记录。

使用工具IntelliJ IDEA 2017.2.3工具创建Maven项目,命名为echoserver,pom.xml内容如下

xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"

xsi:schemaLocation="http://maven.apache.org/POM/4.0.0

http://maven.apache.org/xsd/maven-4.0.0.xsd">

4.0.0

com

echo-server

1.0-SNAPSHOT

echo-server

io.netty

netty-all

4.1.33.Final

创建业务核心处理逻辑EchoServerHandler,内容与注释如下:

package com;

import io.netty.buffer.ByteBuf;

import io.netty.buffer.Unpooled;

import io.netty.channel.ChannelFutureListener;

import io.netty.channel.ChannelHandler;

import io.netty.channel.ChannelHandlerContext;

import io.netty.channel.ChannelInboundHandlerAdapter;

import io.netty.util.CharsetUtil;

@ChannelHandler.Sharable //1.标志这类的实例之间可以再channel里面共享

public class EchoServerHandler extends ChannelInboundHandlerAdapter

{

@Override

public void channelRead(ChannelHandlerContext

ctx, Object msg) throws Exception {

ByteBuf in = (ByteBuf)msg;

System.out.println("Server received:"+in.toString(CharsetUtil.UTF_8));//2.日志输出到控制台

ctx.write(in);//3.将所接收的消息返回给发送者,注意,此时还没有冲刷数据

}

@Override

public void channelReadComplete(ChannelHandlerContext

ctx) throws Exception {

ctx.writeAndFlush(Unpooled.EMPTY_BUFFER)//4.冲刷所有待审消息到远程节点,关闭通道后,操作完成

.addListener(ChannelFutureListener.CLOSE);

}

@Override

public void exceptionCaught(ChannelHandlerContext

ctx, Throwable cause) throws Exception {

ctx.fireExceptionCaught(cause);//5.打印异常堆栈跟踪

ctx.close();//6.关闭通道

}

}

创建完业务核心处理逻辑之后,创建引导服务器EchoServer,作用如下:

监听和接收进来的连接请求;

配置Channel来通知一个关于入站消息的EchoServerHandler实例。

内容如下:

package com;

import io.netty.bootstrap.ServerBootstrap;

import io.netty.channel.ChannelFuture;

import io.netty.channel.ChannelInitializer;

import io.netty.channel.EventLoopGroup;

import io.netty.channel.nio.NioEventLoopGroup;

import io.netty.channel.socket.SocketChannel;

import io.netty.channel.socket.nio.NioServerSocketChannel;

import java.net.InetSocketAddress;

public class EchoServer {

private final int port;

public EchoServer(int port) {

this.port = port;

}

public static void main(String[] args) throws

Exception{

// if(args.length != 1){

// System.err.println("Usage: " + EchoServer.class.getSimpleName()

+ "");

// return;

// }

// int port = Integer.parseInt(args[0]);//1.设置端口值

int port = 8990;//1.设置端口值

new EchoServer(port).start();//2.启动服务

}

public void start() throws Exception{

EventLoopGroup group = new NioEventLoopGroup();//3.创建EventLoopGroup,一个线程

try {

ServerBootstrap b = new ServerBootstrap();

b.group(group)//4.创建ServerBootstrap,此处也可放入多个EventLoopGroup

.channel(NioServerSocketChannel.class)//5.指定使用NIO的传输Channel,指定信道类型

.localAddress(new InetSocketAddress(port))//6.设置socket地址使用所选端口

.childHandler(new ChannelInitializer()

{//7.当有一个新的连接被接受,一个新的子Channel将被创建,ChannelInitializer添加EchoServerHandler到Channel的ChannelPipeline,

@Override

public void initChannel(SocketChannel ch) throws

Exception{

ch.pipeline().addLast(

new EchoServerHandler());

}

});

ChannelFuture f = b.bind().sync();//8.绑定的服务器,sync等待服务器关闭,调用sync()的原因是当前线程阻塞

System.out.println(EchoServer.class.getName()

+ " started and listen on " + f.channel().localAddress());

f.channel().closeFuture().sync();//9.关闭Channel和块

} finally {

group.shutdownGracefully().sync();//10.关闭EventLoopGroup,释放所有资源

}

}

}

服务器的主代码组件是:EchoServerHandler实现了的业务逻辑、在main()方法中引导了服务器。

执行引导服务器所需的步骤是:

创建ServerBootstrap实例引导服务器并随后绑定;

创建并分配一个NioEventLoopGroup实例来市里事件的处理,如接受新的连接和读/写数据;

指定本地InetSocketAddress给服务器绑定;?

通过EchoServerHandler实例给每一个新的Channel初始化;

最后调用ServerBootstrap.bind()绑定服务器。

7.3 写一个echo客户端

客户端要做的就是:

连接服务器;

发送信息;

发送的每个信息,等待和接受从服务器返回的同样的信息;

关闭连接。

用ChannelHandler实现客户端逻辑

跟写服务器一样,Netty提供了ChannelInboundHandler来处理数据,下面的例子中,我们使用SimpleChannelInboundHandler来处理所有的任务,需要覆盖三个方法:

channelActive()--服务器的连接被建立后调用,一旦建立了连接,字节序列被发送到服务器;

channelRead0()--在接收到数据时被调用,由服务器所发送的消息可以以块的形式被接收。即,当服务器发送五个字节是不是保证所有的5个字节会立刻收到,即使只有5个字节,channelRead0()方法可被调用两次,第一次用一个ByteBuf装载3个字节和第二次一个ByteBuf装载2个字节,唯一要保证的是,该字节将按照他们发送的顺序分别被接收;

exceptionCaught()--捕获一个异常时调用。

创建Maven项目,命名echoclient,pom.xml文件内容如下

encoding="UTF-8"?>

xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"

xsi:schemaLocation="http://maven.apache.org/POM/4.0.0

http://maven.apache.org/xsd/maven-4.0.0.xsd">

4.0.0

com

echo-client

1.0-SNAPSHOT

echo-client

io.netty

netty-all

4.1.33.Final

创建EchoClientHandler.java,内容如下

package com;

import io.netty.buffer.ByteBuf;

import io.netty.buffer.Unpooled;

import io.netty.channel.ChannelHandler;

import io.netty.channel.ChannelHandlerContext;

import io.netty.channel.SimpleChannelInboundHandler;

import io.netty.util.CharsetUtil;

@ChannelHandler.Sharable//1.标记这个类的实例可以在 channel

里共享

public class EchoClientHandler extends SimpleChannelInboundHandler

{

@Override

public void channelActive(ChannelHandlerContext

ctx){

ctx.writeAndFlush(Unpooled.copiedBuffer("Netty

rocks!", //2.当被通知该 channel 是活动的时候就发送信息

CharsetUtil.UTF_8));

}

@Override

public void channelRead0(ChannelHandlerContext

ctx, ByteBuf in) throws Exception {

System.out.println("Client received: "

+ in.toString(CharsetUtil.UTF_8));//3.打印接收到的信息

}

@Override

public void exceptionCaught(ChannelHandlerContext

ctx, Throwable cause) throws Exception {

cause.printStackTrace();//4.打印异常堆栈跟踪

ctx.close();//5.关闭通道

}

}

创建引导客户端EchoClient,需要host、port两个参数连接服务器,内容如下

package com;

import io.netty.bootstrap.Bootstrap;

import io.netty.channel.ChannelFuture;

import io.netty.channel.ChannelInitializer;

import io.netty.channel.EventLoopGroup;

import io.netty.channel.nio.NioEventLoopGroup;

import io.netty.channel.socket.SocketChannel;

import io.netty.channel.socket.nio.NioSocketChannel;

import java.net.InetSocketAddress;

public class EchoClient {

private final String host;

private final int port;

public EchoClient(String host, int port) {

this.host = host;

this.port = port;

}

public void start()throws Exception{

EventLoopGroup group = new NioEventLoopGroup();

try {

Bootstrap b = new Bootstrap();//1.创建Bootstrap

b.group(group)//2.指定EventLoopGroup来处理客户端事件,由于我们NIO传输,所以用到了NioEventLoopGroup的实现

.channel(NioSocketChannel.class)//3.使用的Channel类型是一个用于NIO传输,也可以使用和服务器不一样的类型

.remoteAddress(new InetSocketAddress(host, port))//4.设置服务器的InetSocketAddress

.handler(new ChannelInitializer()

{//5.当建立一个连接和一个新的通道时,创建添加到 EchoClientHandler 实例

到 channelpipeline

@Override

public void initChannel(SocketChannel ch)throws

Exception{

ch.pipeline().addLast(new EchoClientHandler());

}

});

ChannelFuture f = b.connect().sync();//6.连接到远程,等待连接完成

f.channel().closeFuture().sync();//7.阻塞直到Channel关闭

} finally {

group.shutdownGracefully().sync();//8.调用shutdownGracefully来关闭线程池和释放所有资源

}

}

public static void main(String[] args)throws Exception{

// if(args.length != 2){

// System.err.println("Usage: " + EchoClient.class.getSimpleName()

+ "");

// return;

// }

// final String host = args[0];

// final int port = Integer.parseInt(args[1]);

final String host = "localhost";

final int port = 8990;

new EchoClient(host,port).start();

}

}

启动Echo服务端,直接运行main()方法,控制台打印如下:

9868d0c4b5853fe728a097a1d7bf8692.png

启动Echo客户端,直接运行main()方法,控制台打印如下:

81076977c75c07aad1d0b34210c54545.png

而在这之前的服务端控制台则会打印如下语句:

95190923d9b26cf9672a47d032fd093e.png

至此一个简单的Netty应用搭建完成.

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/news/431888.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

兩端對齊

1.利用flex parentElement{display: flex;justify-content: space-between;} 左边对齐右边对齐<div class"justifySpan"><span>齐</span><span>齐</span></div> .justify {display: -webkit-box;display: -ms-flexbox;display: …

java拆装_Java自动拆装包

Java自动拆装包的例子这段代码在Java 1.5以前是不合法的Long v 0&#xff1b;v 1&#xff1b;需要写成这样&#xff1a;Long v 0&#xff1b;v new Long(1);在Java 1.5 以后&#xff0c;编译器帮我们做了上面的工作。这就是Java的自动拆装包&#xff0c;方便了很多&#xf…

Android学习(二十)Notification通知栏

一、通知栏的内容 1、图标 2、标题 3、内容 4、时间 5、点击后的相应 二、如何实现通知栏 1、获取NotificationManager。 2、显示通知栏&#xff1a;notify(id,notification); 3、取消通知栏&#xff1a;cancle(id); 4、构造Notification并设置显示内容; 5、通知栏通知可以设置…

java访问mongodb_Java中获取MongoDB连接的方法详解

首先是所需jar包&#xff0c;Maven中的配置如下&#xff1a;org.mongodbmongodb-driver3.4.1org.mongodbbson3.4.1org.springframework.dataspring-data-mongodb1.7.0.RELEASEorg.mongodbmongo-java-driver3.9.1获取连接的代码如下(本中用的是模板类)&#xff1a;List addrs n…

@jsonignore的作用

作用是json序列化时将java bean中的一些属性忽略掉,序列化和反序列化都受影响。 如下&#xff1a; package com.hzboy.orm;import java.util.List;import javax.persistence.CascadeType; import javax.persistence.Column; import javax.persistence.Entity; import javax.per…

java between_Java8 Period.between方法坑及注意事项

在使用Java8 新特性中关于Period.between的方法时需注意该方法获取日期的区间问题。Testpublic void test1(){LocalDate from LocalDate.of(2018,10,1);System.out.println(Period.between(from,LocalDate.now()).getDays());}首先&#xff0c;猜测一下上面的代码返回的天数是…

IT英语2-编程词汇编程英语词汇

IT英语2-编程词汇编程英语词汇 A2A integration A2A整合 abstract 抽象的 abstract base class (ABC)抽象基类 abstract class 抽象类 abstraction 抽象、抽象物、抽象性 access 存取、访问 access level访问级别 access function 访问函数 account 账户 action 动作 activate …

webdriver 爬虫 java_java爬虫通过selenium+WebDriver遍历页面链接报错

背景由于要爬取的页面&#xff0c;每个链接的请求都是点击之后js动态发起的&#xff0c;目标数据也多是js动态生成的&#xff0c;所以使用selenium工具webdriver(调试用的是chrome&#xff0c;具体使用准备用phantomjs).模拟登录之后&#xff0c;模拟查询之后&#xff0c;得到如…

java删除集合元素吗_java如何删除集合中的元素

java如何删除集合中的元素如何使用java删除集合中的元素呢?下面是小编给大家提供的删除集合中元素的常见方法&#xff0c;欢迎阅读&#xff0c;更多详情请关注应届毕业生考试网。Java代码如下&#xff1a;package com.jerval.test;import java.util.ArrayList;import java.uti…

XmlDocument类

XmlDocument类是.NET框架的DOC解析器。XmlDocument将XML视为树状结构&#xff0c;它装载XML文档&#xff0c;并在内存中构建该文档的树状结构。下面来看下XmlDocument提供了哪些功能。 一、属性&#xff1a; Attributes      获取一个 XmlAttributeCollection&#xff0c…

java gc回收算法_Java GC回收算法-判定一个对象是否可以回收

开源推荐推荐一款一站式性能监控工具(开源项目)Pepper-Metrics是跟一位同事一起开发的开源组件&#xff0c;主要功能是通过比较轻量的方式与常用开源组件(jedis/mybatis/motan/dubbo/servlet)集成&#xff0c;收集并计算metrics&#xff0c;并支持输出到日志及转换成多种时序数…

动态规划求一个序列的最长回文子序列(Longest Palindromic Substring )

1、问题描述 给定一个字符串&#xff08;序列&#xff09;&#xff0c;求该序列的最长的回文子序列。 2、分析 需要理解的几个概念&#xff1a; ---回文 ---子序列 ---子串 http://www.cnblogs.com/LCCRNblog/p/4321398.html这一篇文章描述了利用动态规划求解两个序列的最长公共…

java类作用域标识符_java入门 (二) 标识符、数据类型、类型转换、变量、常量、作用域...

java入门(二)标识符数据类型类型转换变量、常量、作用域本次笔记引用B站&#xff1a;狂神说,虽然早就会了&#xff0c;现在回头来敲下基础&#xff0c;加深印象1.标识符&#xff1a;java所有的组成部分都需要名字。类名丶变量名丶方法名统称为标识符。标识符大小写敏感。不能使…

0421 AutoLayout的实践/基本使用

历史:从iOS 6开始 ,之前都是3.5英寸没有考虑到适配.iPhone5 变成了4英寸,所以推出了Auto Layout理解: 另外一个体系,去描述位置.像素:点: // 勘误: 图中的像素应为 “点"// 写上以上代码,就可以删掉系统创建的控制器和storyBoard了.// 创建控制器,勾选Xib[]拖一个uiview背…

C#实现UTC时间与Datetime转换

为了便于传输&#xff0c;通信过程中传输的都是&#xff1a;当前时间跟标准时间相隔的秒数&#xff0c;并且是以16进制字节的形式传输的。 1 public double ConvertDateTimeInt(System.DateTime time)//将时间格式的数据类型转换成浮点数类型 2 {3 doubl…

java selenium iframe_java selenium处理Iframe中的元素示例

java selenium 处理Iframe 中的元素有时候我们定位元素的时候&#xff0c;发现怎么都定位不了。 这时候你需要查一查你要定位的元素是否在iframe里面阅读目录什么是iframeiframe 就是HTML 中&#xff0c;用于网页嵌套网页的。 一个网页可以嵌套到另一个网页中&#xff0c;可以…

des 向量 java_在JAVA中使用DES算法

DES算法提供CBC, OFB, CFB, ECB四种模式&#xff0c;MAC是基于ECB实现的。一、数据补位DES数据加解密就是将数据按照8个字节一段进行DES加密或解密得到一段8个字节的密文或者明文&#xff0c;最后一段不足8个字节&#xff0c;按照需求补足8个字节(通常补00或者FF&#xff0c;根…

可访问性不一致的原因与解决方法

出现原因&#xff0c;其中一个是返回参数的访问级别小于函数的访问级别&#xff0c;也就是说当定义一个返回参数的方法的时候&#xff0c;如果返回参数的访问级别低于方法的访问级别&#xff0c;此时就会出现这样的错误。如果返回的参数不能被访问,那么定义的返回的方法也是错误…

jQuery 事件 - bind() 方法

定义和用法 bind() 方法为被选元素添加一个或多个事件处理程序&#xff0c;并规定事件发生时运行的函数。 实例1&#xff08;一个事件&#xff09; 记得把js引用地址换掉 当点击鼠标时&#xff0c;隐藏或显示 p 元素&#xff1a; <html><head><script type"…

java 圆形按钮,如何在Java中创建圆形的JButton?

I want to create rounded JButton in Java...For that I use rounded image and placed that image on button but I didnt get rounded button..please any one can tell how to create rounded button in Java like show in below figure..thanks in advance.....解决方案If…