web客户端与服务器实时通信的方法

1 刷新,但是开销太大

2 客户端使用java applet
采用java applet技术与第一种方法类似,它只是将大多数编程操作封装在java小程序中,客户端在取到包含小程序引用的网页时,先去指定的服务器下载小程序到本地,然后执行它,由小程序建立与服务器的连接,并进行信息的收转工作

3 使用控件,如microsoft的winsock控件
http://www.xici.net/u1646037/d31903083.htm

4 xmlHTTP
http://www.cnblogs.com/geoff/archive/2007/03/19/679959.html

XMLHTTP应用

 

Xmlhttp 是一种浏览器对象,可用于模拟 http GET POST 请求。配合 JavaScript 可以实现页面数据在无刷新下的定时数据更新,如果应用在聊天室、文字直播上可以取得较好的视觉效果。

 

一、使用步骤:

1、   创建 XMLHTTP对象

2、   打开与服务端的连接,同时定义指令发送方式,服务网页 (URL)和请求权限等。客户端通过 Open命令打开与服务端的服务网页的连接。与普通 HTTP指令传送一样,可以用 "GET"方法或 "POST"方法指向服务端的服务网页。

3、   发送指令。

4、   等待并接收服务端返回的处理结果。

5、   释放 XMLHTTP对象      

     

三、 XMLHTTP方法:      

方法

描述

abort()

停止当前请求

getAllResponseHeaders()

作为字符串返问完整的 headers,这里的 header是指从服务器返回的头部

getResponseHeader("headerLabel")

作为字符串返问单个的 header标签 ,这里的 header是指从服务器返回的头部

open( bstrMethod, bstrUrl,varAsync,

      [bstrUser, bstrPassword]

 

bstrMethod: 数据传送方式,即 GET POST

bstrUrl   服务网页的 URL

varAsync:是否同步执行。缺省为 True,即同步执行,

但只能在 DOM中实施同步执行。用中一

般将其置为 False,即异步执行。

bstrUser: 用户名,可省略。

bstrPassword:用户口令,可省略。

send( varBody

varBody:指令集。可以是 XML格式数据,也可以是字符串,流,或者一个无符号整数数组。也可以省略,让指令通过 open方法的 URL参数代入。 通常情况下,如果是用 GET方式提交,可以用 xmlobj.send(null)发送 , 因为此时要提交的数据已经放在 url后面了

setRequestHeader( bstrHeader,

                  bstrvalue

bstrHeader HTTP (header)

bstrvalue HTTP (header)的值

如果 Open方法定义为 POST,可以定义表单方式上传:

xmlhttp.setRequestHeader "Content-Type",

    "application/x-www-form-urlencoded"

 

 

 

三、                       XMLHTTP属性:

 

属性

描述

onreadystatechange

状态改变的事件触发器 , 在同步执行方式下获得返回结果的事件句柄,该句柄最好在 send之前定义,否则会出错。

readyState

对象状态 (integer):

0 = 未初始化

1 = 读取中

2 = 已读取

3 = 交互中

4 = 完成

responseText

服务器进程返回数据的文本 字符串

responseXML

服务器进程返回数据的兼容 DOM XML文档 对象 , 这时你可以直接用 DOM操作它了。

status

服务器返回的状态码 , :

404 = "文件末找到 "

200 ="成功 "

statusText

服务器返回的状态文本信息

responseStream

  结果返回为 IStream流。

 

四、                       示例:

       A)

<script language="javascript">

function getDatal(url, data)

{

          var result = null;

var xmlhttp = new ActiveXObject("Microsoft.XMLHTTP"); //创建 XMLHTTPRequest对象

xmlhttp.open("GET",url,false);           //使用 HTTP GET初始化 HTTP请求

 

//设置头部信息,让它用 utf-8发送,不然中文可能会乱码

xmlhttp.setrequestheader("content-type","application/x-www-form-urlencoded");

xmlhttp.onreadystatechange = function()

{

             if ( xmlhttp.readyState == 4 && xmlhttp.status == 200 )

                        result = xmlhttp.responseXML;            //得到返回信息

}

 

xmlhttp.send(data);                      //发送 HTTP请求并获取 HTTP响应

return result;                           //返回结果

}

</script>

 

B)

<html>

<head><title>自动刷新 </title>

<script language="javascript">

function detect()

{

xml = new ActiveXObject("Microsoft.XMLHTTP"); 

var post="数据数据 ";              //构造要携带的数据  

 

//使用 POST方法打开一个到服务器的连接,以异步方式通信

xml.open("POST","link.php",false);

xml.setrequestheader("content-length",post.length); 

xml.setrequestheader("content-type","application/x-www-form-urlencoded"); 

 

xml.send(post);            //发送数据  

var res = xml.responseText;              //接收服务器返回的数据

 

var list = document.getElementById( "list" );

list.innerText = res;

setTimeout( detect() ,5000);    //每隔 5秒钟轮询一次

</script>

<body οnlοad= detect() >

<a id="list"></a>

</body>

</html>

 

五、要注意的问题

特别要注意的是由于 IE Cache 的关系,我们看见的 XmlHttp 并不总是最新读取的那一个,为了让 IE 不启用 Cache,我们发送给 IE 一个特殊的 Header(这里的 header是指后台处理该请求的页面),用 PHP 实现如下:

header( "Expires: Mon, 26 Jul 1997 05:00:00 GMT" );

header( "Last-Modified: " . gmdate( "D, d M Y H:i:s" ) . "GMT" );

header( "Cache-Control: no-cache, must-revalidate" );

header( "Pragma: no-cache" );

 

使用 JavaScript 实现 XmlHttp 的跨浏览器应用

Mozilla IE同样支持 XMLHttpRequest ,不过在使用过程中是不一样的 .

1. Mozilla 浏览器自带了 XMLHttpRequest 接口

new XMLHttpRequest()

2. IE 需要使用 ActiveX对象来建立 .

new ActiveXObject("Microsoft.XMLHTTP")       //IE5

new ActiveXObject("Msxml2.XMLHTTP")          //IE6+

为了能在多种浏览器上有一个统一的实现,我们可以用 JavaScript 来对不同浏览器的差异进行封装。这里我们采用这样实现 :

Var oHttp = window.ActiveXObject? new ActiveXObject("Microsoft.XMLHTTP"):

                                   new XMLHttpRequest();

这样, Js 脚本允许我们在 IE Gecko Mozilla/FireFox ) 和 Opera 的特定版本使用 XmlHttp 。下边是调整后的 loadFragmentInToElement 函数,这个函数在 IE6 FireFox1.0pre 上运行通过。

 

XmlHttp 中的中文乱码问题

在默认情况下, XmlHttp 都是使用 Utf-8 字符集,而我们使用的多是 GB2312 字符集,这就要求我们进行 GB2312 Utf-8 的转码。 PHP 提供了一个可选的专码模块,可以实现多种字符集之间的相互转化。加载这个专码模块的方法如下:

打开 PHP 配置文件 php.ini,将 ;extension=php_mbstring.dll linux php_mbstring.so)前的分号去掉。重新启动 Apache 以后,这个模块就可以使用了。如果有错误出现,请检查扩展目录的路径设置是否正确。

加载这个模块以后,我们就可以使用 mb_convert_encoding 函数来转码了:

$utf8_string = mb_convert_encoding( $gb_string , 'UTF-8' , 'GB2312' );

将转码后的字符输出就可以看见正确显示的中文了

 

发送大量 XML数据

在把大量的 XML作为 POST数据的一部分发送给你的 IIS服务器的时候——诸如在 ASP表单的 TEXTAREA里——你可能会得到一些没有预料到的结果。当数据在服务器上被处理的时候,由于你处理数据方式的不同,你最终可能会碰到错误。其原因是,当你把数据提交回服务器的时候, POST字段里有一个(数据)大小的限制。这样做的目的是为了防止可能的入侵者在实施拒绝服务( denial of service DoS)的攻击中向服务器发送超大量的数据。

 

这一限制也束缚你的能力。但是有办法解决这个问题。如果你没被限制在只能够通过 FORM提交来发送数据,那么你就可以使用 XMLHTTP对象(微软的 XML集里的一个 DOM对象)来发送所需要的 XML

 

var oXMLHTTP = new ActiveXObject("Microsoft.XMLHTTP");

oXMLHTTP.open("POST", "xml_handler.asp", false);

oXMLHTTP.send(xml_to_send);

 

如果你被限制在只能够使用 FORM提交,那么你可以通过提交多个 TEXTAREA或者 INPUT来跨越这一限制,前面两者在服务器一接收到这个 FORM数据的时候就可以被重新组合在一起:

<script language="javaScript">

var MAXLEN = 90000;

var oForm = document.createElement("FORM");

oFORM.method = "POST";

oFORM.action = "xml_handler.asp";

oFORM = document.body.appendChild(oFORM);

var s = document.someForm.txtXML.value;

if (s.length > MAXLEN)

{

    while ( s.length > MAXLEN )

{

        var o = document.createElement("INPUT");

        o.type = "hidden";

        o.name = "txtXML";

        o.value = s.substr(0, MAXLEN);

        oFORM.appendChild(o);

        s = s.substr(MAXLEN);

    }

    var o = document.createElement("INPUT");

    o.type = "hidden";

    o.name = "txtXML";

    o.value = s.substr(0, MAXLEN);

    oFORM.appendChild(o);

}

else

{

    var o = document.createElement("INPUT");

    o.type = "hidden";

    o.name = "txtXML";

    o.value = s;

    oFORM.appendChild(o);

}

</script>

 

这一段代码会创建一个新的 FORM元素,用来处理数据的提交,并将它放置到 BODY元素内。然后,它会检查即将提交给服务器的 XML的长度。这个 XML驻留在 someForm内部一个叫做 txtXML TEXTAREA里。

 

如果这个 XML大于 90,000字符的 MAXLEN,那么这段代码就会创建多个隐藏的 INPUT(输入)元素,并把值的属性设置为 90,000个字符的 XML数据,或者设置为 XML尾部的某个值,从而将这个数据分割成多个部分。如果这个 XML的大小小于 MAXLEN,那么这段代码就只会创建一个 INPUT并相应地设置值。然后这个数据就被提交到服务器供处理。

你可能已经注意到,我把相同的名称—— txtXML——指定给新表单的每个字段。这将有助于把 XML数据同其他可能会被提交的数据分隔开来,并为重组 XML数据提供了一种简单的方式。在重组数据的时候,你需要一个简单的循环来连接字段里的数据 .

由于已经为每个 FORM元素都创建了一个字段集,所以你可以在同一个名称的字段里迭代。只要以适当的顺序在客户端创建 FORM元素,你就不需要担心字段被遍历的顺序。通过 FORM appendChild()方法,这能够被轻易地实现。

数据在客户端是按照从左到右、从上到下的顺序被提交的,所以当你把 INPUT元素附加到 FORM元素尾部的时候,在你服务端也总是按照同样的顺序来接收数据的。

 

如果你正在寻求实现一个大型的数据解决方案,例如将大量的 Excel数据从客户机器传递到服务器上,那么你就应该重新考虑是否要使用 FORM提交,或者将数据从逻辑上分成多个小的部分。由于你无法使用文件类型 INPUT元素,所以最具有创造力的解决方案是将数据在本地转变成为 XML,再将 XML数据提交给服务器。反过来,数据会保存在服务器上,直到需要更进一步处理。

 

当然,处理这个问题可能会有更好的方法。但是当你没有太多时间的时候,你所需要的就是一个快速的、可用的解决方案。

 

  var objDom = new ActiveXObject("MICROSOFT.XMLDOM")

  objDOM.loadXML("<root><action>Inquiry</action><data/></root>");

添加节点到 Dom对象 objDom

  var objNodeChild;

  objNodeChild = objDom.createElement(strNodeName); //strNodeName是要新增节点的名称

  objNodeChild.text = strNodeValue;           //strNodeValue是要新增节点的值

 

//strNodeParent是要添加节点的父节点的路径 ;

objDom.selectSingleNode(strNodeParent).appendChild(objNodeChild);

 

  //或者是添加属性到存在的节点

  var objNewAttr;

  objNewAttr = objDom.createAttribute(strAttrName)

  objNewAttr.text = strAttrValue

  objDom.selectSingleNode(strNode).Attributes.setNamedItem(objNewAttr)

 

使用 xmlHttp

//创建 xmlHttp对象

var objHttp = new ActiveXObject("MICROSOFT.XMLHTTP");

objHttp.open("POST",strAspPageName,false);   //false 代表不异步处理

objHttp.setRequestHeader("Content-Type","application/x-www-form-urlencoded");

 

//传递 Dom对象到指定页面

objHttp.send(objDom);

 

//接受指定页面处理之后的 Dom对象

objDom.load(objHttp.ResponseStream);

//之后就可以对 objDom中的数据进行操作

 

 

 

XML介绍之二十八: XMLHTTP: 网站超级粘合剂    

简介

许多 ASP开发者都希望在自己的网站中能够使用到微软提供的支持 XML的新功能。其中,有些人发现可以使用 XML来装饰网站,但是,如果仅仅是只使用 XMLDOM的话,你就会失去其他一些更重要的东西。毕竟, XML是用来作为一种网上数据表现和数据交换的形象出现的。

尽管使用 XML可以非常满意地描绘你的数据,但是开发者却不得不使用 CGI来进行浏览器和服务器之间的数据交换,除非你在浏览器端和客户端都使用 XML文档。

当然 CGI从传达信息的角度来说是能够完全胜任的,但是如果要是和 XML来一起使用的话就让 XML失去了很多自己的用处。幸运的是,微软提供了一种更加有效的方法来传输 XML,虽然该方法在很大程度上并不被人所重视。

在微软提供的 MSXML解释器包中有一系列的对象,也许没有人会重视其中 XMLHTTPConnection对象。简而言之,它允许你打开一个到服务器上的 HTTP连接,

发送一些数据和取回一些数据。并且所有的这一切都是在很少的几段脚本中就能够实现。

使用 XMLHTTP对象通常是进行 XML数据交换,但其他格式的数据也是允许的。    

这种交换类型的标准模式是客户端发送一个 XML格式的文本字符串到服务端,然后服务端将这个字符串装载入一个 XMLDOM对象中并且解释它,然后返回一段 HTML给客户端,或则是另外一段 XML代码给客户端让客户端的浏览器自己解释。

  在这种方式下,对于信息的传递来说是非常有效的形式,尤其是当你使用 DHTML允许你根据返回信息动态显示时。

   举例如下(只能够运行在客户端和服务端都安装有 IE5的情况下)

<%

   if (Request.ServerVariables("REQUEST_METHOD") == "POST" )

   {

          var req = Server.CreateObject("Microsoft.XMLDOM");

          req.async = false;

          req.load(Request);

          if (req.documentElement.nodeName=="timesheet")

          {

                 //对数据随便进行一些处理。。。

                 .....

                 Response.write( "<h1>Timesheet Updated!</h1><b>"

+ req.documentElement.text+"</b>" );

          }

   }

   else

   {

%>  

   <div id="divDisplay">The response will be put in here</div>

   <input type="button" οnclick="sendData();" value="Send it!">

   <script language="javaScript">

   function sendData()

  {

          var xmlhttp = new ActiveXObject("Microsoft.XMLHTTP");

          xmlhttp.Open("POST", "http://www.yoursite.com/thispage.asp", false);

          xmlhttp.Send("<timesheet>An impossibly useless timesheet fragment</timesheet>");

          divDisplay.innerHTML=xmlhttp.responseText;

   }

   </script>

<%

}

%>

  

在上面的代码中,其中客户端的脚本将建立一个适当的 COM对象,打开一个在网站 www.yoursite.com的连接(使用了 HTTP POST方法,同步方式),使用 Send方法发送一个 XML片段,然后根据服务器上的响应填充 divDisplay区域(这里使用了 DHTML)。

具体的执行过程是,在服务器上, Request对象被转载入一个 XML文档然后被解释器解释。服务器响应 XMLHTTP连接的方式和响应其他任何方式的 HTTP连接是一样的,也是使用了 Response对象。注意的是 XMLHTTP本身并不检查 request或则 response的有效性,也就是说 Request或则 Response中的数据可是并不需要一定是 XML文档。

   “聪明,”你也许会说。“但是为什么我们不使用 CGI来代替它呢?”呵呵,我们要注意这样一件事,就是如果使用这种方式进行客户端 --服务端的交互时整个页面并没有被刷新。

  我们都知道,如果要是通过 CGI来做任何事情都必将导致浏览器接收一个完整的新页面,而这尤其影响网站上的访问者,因为他们不得不把所有的时间都用来等候整个页面下载完毕。

  同样, CGI对于网站服务器来说也是一个负担,因为它不得不把宝贵的处理器循环周期和带宽消耗在新页面的所有部分。如果这样的操作只是一次或则两次倒无所谓,但是如果是对任何一个电子商务网站或则一个基于 Web的电子邮件系统,这将意味着大量的同样的基本页面信息被重复一次又一次的装载。

同样,如果是通过 CGI在网站运用程序中使用 XML,服务端一般都将不得不根据数据来建立 XML的文档,然后才能够对这些文档进行自己需要的处理。在这种方式下,服务器将花费大量的精力在处理如何建构这些 XML文档上,尤其是当需要传送的数据量很大时。

所以如果是让客户端的浏览器来建立这个 XML文档,并且在建立完毕后通过 XMLHTTP将最后的产品传递给服务器,这将大大减轻服务端的代码量和负担。

这种类型的问题的一个例子是给服务器上的 XML文档增加数据。如果是使用 CGI的话,那么就需要频繁的查询一个 CGI form,然后才能够构建一个加入 XML文档的 XML节点。而如果是使用 XMLHTTP需要做的仅仅是把这个 XML节点传递给服务端就可以了。   

上面说讨论的是 XMLHTTP基本部分,有关它的详细例子你可以在 Microsoft Developers Network中找到例子 。虽然使用这种通讯方式可以大有作为,我在我自己的运用中仅仅只是使用到了很少的一部分,也许任何一个聪明的开发者都能够发现更多的运用事例。    

使用 XMLHTTP而不是 CGI(即使是我们心爱的 ASP)能够让我编写更多野心勃勃的网站运用程序,因为现在我们所关心的简单到只是我们需要发送的数据而已。从而使用很少的代码就能够实现非常复杂的功能,而 CGI对于用户每一个可能的操作都需要我们来完完整整地生成一个新的页面。

但是由于目前并不是所有的浏览器都支持 MSXML,许多使用 ASP编写的为了非企业内部目的的运用程序需要支持 CGI的交互。但是欣慰的是,编写一个同时支持 CGI XMLHTTP数据的页面并不是很困难,并且将 CGI的数据载入 XML文档中花费的工作量也不是很大。

最简单的方式来判断数据是 CGI的数据还是 XML的数据就是判断数据的 MIME类型 .

XMLHTTP MIME是一个空字符串,除非你特定了其他的 MIME类型 .

  而许多 CGI MIME类型是 "application/x-www-form-urlencoded"

  下面就是一个来判断的代码片段:    

  <% if (Request.ServerVariables("REQUEST_METHOD") == "POST" )

  {

   if (Request.ServerVariables("CONTENT_TYPE")=="application/x-www-form-urlencoded")

   {

//如果是常规数据 (通常编码是 utf-8),让 CGI来处理

    Response.write(Request.form("stuff"));   

     }

   else

{

//如果是 XMLHTTP连接 , Request对象转载入 XML解释器

          var req= Server.CreateObject("Microsoft.XMLDOM");

          req.resolveExternals=false;

          req.validateOnParse=false;

          req.async=false;

          req.load(Request);

          Response.write(req.documentElement.selectSingleNode("stuff").text);

     }

  }

  else{ %>

  

   这是一种简单明了的在同一个 ASP页面中即可以处理 CGI也可以处理 XMLHTTP数据的方法。并且它也提供了一种能够兼容在客户端安装了 IE5.0以及使用其他其他浏览器浏览网站的模式。或则也可以采取另外一种方法,就是我对所有的网站运用程序还是采用以前的 CGI接口,但是在其他类型的客户端运用程序使用 XMLHTTP方法,例如 Microsoft Office运用程序。 XMLHTTP的功能并不仅仅局限在浏览器上,我在 Microsoft Office VBA开发程序中使用 XMLHTTP取得了巨大的成功。现在我假设我被要求使用 XML技术在更新我公司服务器上的 Excel电子表格中的数据。 Excel能够将 HTML表格直接转载到自己的表格中,但是它不能够处理格式复杂的页面。数据除非使用了非常巧妙的技巧,否则根本没法插入电子表格。

我的解决方法是编写了一个 ASP页面来操纵通过 XMLHTTP Excel中传递过来的数据。通过一个 VBA的宏给服务器发送一个请求,然后将响应载入 XML文档,通过解释器解释后再插入 Excel的电子表格中。这将是一个无痕的解决方案,简单的一个按钮也许会让你的老板、同事或任何其他人的关系大有改观。

下面是我实现上述方法的一个代码片段。它使用 XMLHTTP将服务器中的信息载入,然后将其插入电子表格中。

  

Public Sub UpdateSheet()   

Dim xmlhttp

Set xmlhttp = CreateObject("Microsoft.XMLHTTP")

Call xmlhttp.Open("POST", "http://www.yourserver.com/yourpage.asp", False)

Call xmlhttp.send("<reqtimesheet user='jimbob'/>")   

Dim xmldoc

Set xmldoc = CreateObject("Microsoft.XMLDOM")

xmldoc.async = False

xmldoc.loadxml(xmlhttp.responsexml)

   Worksheets("TimeSheet").Range("A1").Value =

xmldoc.documentelement.getAttribute("firstname")

Worksheets("TimeSheet").Range("B1").Value =

xmldoc.documentelement.getAttribute("lastname")

Worksheets("TimeSheet").Range("C37").Value =

xmldoc.documentelement.selectSingleNode("totalhours").Text

End Sub

  

这个 VBA的宏相当的简单。给服务器发送一个请求,然后将服务器上的响应插入 XML文档,然后更新 Excel cell中的内容。当然,我们可以使用这个技术做其他更多的运用。例如从一个 Office运用程序中上载数据到服务器上的 XML文档中 (XML应该是你首选的格式,而不是 Office 2000中提供的愚蠢的 OfficeXML实现 ).或则把 XML/ASP作为一个你数据库的 shell。这样,你的运用程序对于数据库就有了一个简洁、统一的接口,而对数据库结构的改动就不必要改动你所有的客户端代码了。

  

我发现 XMLHTTP对象在我的编程中非常的有用。我一般使用 Visual Basic, Delphi, Visual J++编写程序,在这个过程中,我经常发现这些语言各自对在线程序处理的方法非常地不同,他们各自有自己的对网络程序的处理机制,但是如果你要是在处理网络程序时都使用统一的 XMLHTTP连接方式,那么连接服务器的代码将非常小,甚至更优化,这是一种对所有的语言都统一的接口。

 

再来一例 :

使用到的是 XMLDOM XMLHTTP对象 .用这种技术的好处是 : JS控制 ,方便 /简单 , RDS或者 remote好多了 .

function Send(Str,URL)

{

          //STR参数是传入的 XML数据 ,你也可以传入其他文本数据 .

//不过这个函数需要服务器端处理之后返回 XML数据 ,你也可以修改一下

//URL参数表示你所要处理数据的 ASP文件地址

var Http = new ActiveXObject("Microsoft.XMLHTTP") //建立 XMLHTTP对象

var Dom = new ActiveXObject("Microsoft.XMLDOM") //建立 XMLDOM对象

 

Http.open("POST",URL,false)

//第一个参数的意思是 , "POST"方式发送数据 .可以大到 4MB,也可以换为 "GET".只能 256KB

// 2个参数的意思是数据发送到哪个文件处理

// 3个参数意思是同步或异步方式 .TRUE为异步 ,FALSE为同步

Http.send(Str) //开始发送数据 .............嘟嘟 ..

Dom.async=false //设置为同步方式获取数据

Dom.loadXML(Http.responseText)

//开始获取服务器端处理后返回的数据 .我在这里设置必须为 XML数据 ,否则出错 .

//你也可以自己修改 .使返回的是 2进制或者记录集数据 ...........................……

 

if(Dom.parseError.errorCode != 0) //检查是否发生获取数据时错误

{

delete(Http)

delete(Dom)

return(false)

}

else

{

var Back = Dom.documentElement.childNodes.item(0).text

//得到返回的 XML数据 ,我这里假设处理程序只返回一行 XML数据 (一个节点 )

delete(Http)

delete(Dom)

return(Back) //函数返回数据 .......................结束

}

}

 

var CAT = Send("<user><name>谢柠檬 </name></user>","TEST.PHP");   //执行函数

if (CAT == false)

alert("对不起 .处理程序返回的是 FALSE.数据处理已经失败 ........");

else if( eval(CAT) )

alert("OK.数据已经发送成功 .兼以处理完成 !!!!!!");

else

alert("对不起 .处理程序返回的是 FALSE.数据处理已经失败 ........");



评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值