让你的APP和你的服务器畅快通讯
做安卓开发有很多时候都是要和web交互的,我们很难制作本地应用,这次把小弟整出来的安卓和服务器通讯贡献出来,希望能帮到需要的朋友,同时也是加深印象。
我们先来搭建安卓客户端,首先写好布局文件:
1.布局文件Register.xml:
- <?xml version="1.0" encoding="utf-8"?>
- <LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
- android:layout_width="fill_parent"
- android:layout_height="fill_parent"
- android:background="@drawable/fuction_fond_bg"
- android:orientation="vertical" >
- <ImageView
- android:layout_width="fill_parent"
- android:layout_height="wrap_content"
- android:src="@drawable/setting_btn" >
- </ImageView>
- <ScrollView
- android:layout_width="wrap_content"
- android:layout_height="wrap_content" >
- <LinearLayout
- android:layout_width="fill_parent"
- android:layout_height="wrap_content"
- android:layout_gravity="center_horizontal"
- android:orientation="vertical" >
- <TextView
- android:layout_width="fill_parent"
- android:layout_height="wrap_content"
- android:text="请输入您的注册信息:"
- android:textColor="#6495ED"
- android:textSize="20dip" >
- </TextView>
- <View
- android:layout_width="fill_parent"
- android:layout_height="2dip"
- android:background="#FF909090" />
- <LinearLayout
- android:layout_width="fill_parent"
- android:layout_height="wrap_content"
- android:layout_margin="20dip"
- android:background="#FFFFFF"
- android:orientation="vertical"
- android:padding="10dp" >
- <LinearLayout
- android:layout_width="wrap_content"
- android:layout_height="wrap_content"
- android:orientation="horizontal" >
- <TextView
- android:layout_width="wrap_content"
- android:layout_height="wrap_content"
- android:text="帐 号: "
- android:textColor="#6495ED" >
- </TextView>
- <EditText
- android:id="@+id/username"
- android:layout_width="190dip"
- android:layout_height="wrap_content" >
- </EditText>
- </LinearLayout>
- <View
- android:layout_width="fill_parent"
- android:layout_height="2dip"
- android:background="#FF909090" />
- <LinearLayout
- android:layout_width="wrap_content"
- android:layout_height="wrap_content"
- android:orientation="horizontal" >
- <TextView
- android:layout_width="wrap_content"
- android:layout_height="wrap_content"
- android:text="密 码: "
- android:textColor="#6495ED" >
- </TextView>
- <EditText
- android:id="@+id/password"
- android:layout_width="190dip"
- android:layout_height="wrap_content"
- android:password="true" >
- </EditText>
- </LinearLayout>
- <View
- android:layout_width="fill_parent"
- android:layout_height="2dip"
- android:background="#FF909090" />
- <LinearLayout
- android:layout_width="wrap_content"
- android:layout_height="wrap_content"
- android:orientation="horizontal" >
- <TextView
- android:layout_width="wrap_content"
- android:layout_height="wrap_content"
- android:text="确认密码 : "
- android:textColor="#6495ED" >
- </TextView>
- <EditText
- android:id="@+id/confirmpsw"
- android:layout_width="190dip"
- android:layout_height="wrap_content"
- android:password="true" >
- </EditText>
- </LinearLayout>
- <View
- android:layout_width="fill_parent"
- android:layout_height="2dip"
- android:background="#FF909090" />
- <LinearLayout
- android:layout_width="wrap_content"
- android:layout_height="wrap_content"
- android:orientation="horizontal" >
- <TextView
- android:layout_width="wrap_content"
- android:layout_height="wrap_content"
- android:text="昵 称: "
- android:textColor="#6495ED" >
- </TextView>
- <EditText
- android:id="@+id/nikename"
- android:layout_width="190dip"
- android:layout_height="wrap_content" >
- </EditText>
- </LinearLayout>
- <View
- android:layout_width="fill_parent"
- android:layout_height="2dip"
- android:background="#FF909090" />
- <LinearLayout
- android:layout_width="wrap_content"
- android:layout_height="wrap_content"
- android:orientation="horizontal" >
- <TextView
- android:layout_width="wrap_content"
- android:layout_height="wrap_content"
- android:layout_marginTop="5dp"
- android:text="性 别: "
- android:textColor="#6495ED" >
- </TextView>
- <RadioGroup
- android:id="@+id/gender_group_rb"
- android:layout_width="fill_parent"
- android:layout_height="wrap_content"
- android:orientation="horizontal" >
- <RadioButton
- android:id="@+id/male_rb"
- android:layout_width="wrap_content"
- android:layout_height="wrap_content"
- android:text="男 "
- android:textColor="#6495ED" >
- </RadioButton>
- <RadioButton
- android:id="@+id/female_rb"
- android:layout_width="wrap_content"
- android:layout_height="wrap_content"
- android:text="女"
- android:textColor="#6495ED" >
- </RadioButton>
- </RadioGroup>
- </LinearLayout>
- <LinearLayout
- android:layout_width="wrap_content"
- android:layout_height="wrap_content"
- android:orientation="horizontal" >
- <ImageView
- android:layout_width="fill_parent"
- android:layout_height="wrap_content" >
- </ImageView>
- </LinearLayout>
- <View
- android:layout_width="fill_parent"
- android:layout_height="2dip"
- android:background="#FF909090" />
- <Button
- android:id="@+id/register_btn"
- android:layout_width="fill_parent"
- android:layout_height="40dp"
- android:layout_margin="10dp"
- android:background="@drawable/new_button_bg"
- android:gravity="center"
- android:text="注 册" />
- </LinearLayout>
- </LinearLayout>
- </ScrollView>
- </LinearLayout>
2.Activity文件:RegisterActivity.java
为了让大家看得方便,我逐个为大家讲解:
1.初始化视图控件:
- /**
- * 初始化视图控件
- */
- private void initView() {
- username_et = (EditText) findViewById(R.id.username);
- password_et = (EditText) findViewById(R.id.password);
- confirmpsw_et = (EditText) findViewById(R.id.confirmpsw);
- nikename_et = (EditText) findViewById(R.id.nikename);
- register_btn = (Button) findViewById(R.id.register_btn);
- register_btn.setOnClickListener(listener);
- gender_group_rb = (RadioGroup) findViewById(R.id.gender_group_rb);
- gender_group_rb.setOnCheckedChangeListener(checkListener);
- }
2.当我们填写好数据后,点击注册按钮,调用注册这个方法:
- /**
- * 注册按钮的点击
- */
- private OnClickListener listener = new OnClickListener() {
- @Override
- public void onClick(View v) {
- doRegister();
- }
- };
- /**
- * 开始注册
- */
- private void doRegister() {
- pd = ProgressDialog.show(RegisterActivity.this, "正在注册..",
- "正在注册中..请稍后....", true, true);
- // 1.获取数据
- username = username_et.getText().toString();
- password = password_et.getText().toString();
- confirmpsw = confirmpsw_et.getText().toString();
- nickname = nikename_et.getText().toString();
- // 2.进行校验,不对返回,否则继续
- if (checkNull(username) || checkNull(password) || checkNull(confirmpsw)
- || checkNull(gender) || checkNull(nickname)) {
- Toast.makeText(this, "请填写完整数据", Toast.LENGTH_SHORT).show();
- // TODO 这里本应该完整校验的,暂时偷懒
- return;
- }
- // 3.开始向服务器注册
- Thread thread = new Thread(registerRunnable);
- thread.start();
- }
因为做的比较简陋,详细的表单校验没有写,点击注册开启一个子线程来处理和服务器打交道的耗时操作。在注册的过程中用的httpUrlConnection连接服务器,向服务器提交注册信息。
- /**
- * 开始注册的线程
- */
- Runnable registerRunnable = new Runnable() {
- @Override
- public void run() {
- // 1.拼装数据
- StringBuilder sb = new StringBuilder();
- sb.append("<users>");
- sb.append("<user>");
- sb.append("<username>");
- sb.append(username);
- sb.append("</username>");
- sb.append("<password>");
- sb.append(password);
- sb.append("</password>");
- sb.append("<nickname>");
- sb.append(nickname);
- sb.append("</nickname>");
- sb.append("<gender>");
- sb.append(gender);
- sb.append("</gender>");
- sb.append("</user>");
- sb.append("</users>");
- // 2.开始写数据
- byte content[] = sb.toString().getBytes();
- try {
- URL url = new URL(Constant.REGISTER_SERVLET);
- HttpURLConnection conn = (HttpURLConnection) url
- .openConnection();
- conn.setDoInput(true);
- conn.setDoOutput(true);
- conn.setRequestMethod("POST");
- conn.setRequestProperty("Content-Type", "mutipart/form-data");
- conn.setRequestProperty("Content-Length", content.length + "");
- conn.getOutputStream().write(content);
- // 3.获取服务器返回的数据
- if (conn.getResponseCode() == HttpURLConnection.HTTP_OK) {
- InputStream in = conn.getInputStream();
- RegisterResultTool resultTool = new RegisterResultTool();
- String result = resultTool.getResultFromInputStream(in);
- // 4.提交结果
- Message msg = new Message();
- msg.obj = result;
- msg.what = 200;
- registerResultHandler.sendMessage(msg);
- }
- } catch (IOException e) {
- Message msg = new Message();
- msg.what = 400;
- registerResultHandler.sendMessage(msg);
- e.printStackTrace();
- }
- pd.cancel();
- }
- };
向服务器提交数据后,服务器会返回一些结果数据,我们就需要处理这些结果数据:
- /**
- * 处理服务器返回结果的类
- *
- * @author Larson
- *
- */
- private class RegisterResultTool {
- /**
- * 从服务器返回的数据中读取返回结果
- *
- * @param in
- * @return
- */
- public String getResultFromInputStream(InputStream in) {
- String result = "";
- SAXParserFactory sf = SAXParserFactory.newInstance();
- try {
- XMLReader xr = sf.newSAXParser().getXMLReader();
- RegisterResultHandler rrh = new RegisterResultHandler();
- xr.setContentHandler(rrh);
- xr.parse(new InputSource(in));
- result = rrh.getResult();
- } catch (Exception e) {
- e.printStackTrace();
- }
- return result;
- }
- }
- /**
- * 因为服务器返回的是xml形式,所以需要解析
- *
- * @author Larson
- *
- */
- private class RegisterResultHandler extends DefaultHandler {
- /**
- * 获得的服务器返回结果
- */
- private String result;
- /**
- * 临时存取数据的变量
- */
- private String var="";
- /**
- * 获取返回值
- *
- * @return
- */
- public String getResult() {
- return result;
- }
- @Override
- public void startElement(String uri, String localName, String qName,
- Attributes attributes) throws SAXException {
- super.startElement(uri, localName, qName, attributes);
- }
- @Override
- public void characters(char[] ch, int start, int length)
- throws SAXException {
- var += new String(ch, start, length);
- super.characters(ch, start, length);
- }
- @Override
- public void endElement(String uri, String localName, String qName)
- throws SAXException {
- /**
- * 取出info标签的数据(服务器返回的注册结果)
- */
- if (qName.equals("info")) {
- result = var.trim();
- }
- super.endElement(uri, localName, qName);
- }
- }
获取结果后,在handler中刷新ui通知用户:
- /**
- * 处理返回结果的handler
- * 如果返回的数据是服务器给的成功数据,注册成功,否则就是服务器有问题
- */
- private Handler registerResultHandler = new Handler() {
- public void handleMessage(Message msg) {
- System.out.println(msg.obj+"-------------"+msg.what);
- switch (msg.what) {
- case 400:
- Toast.makeText(RegisterActivity.this, "注册失败.", Toast.LENGTH_SHORT).show();
- break;
- case 200:
- String str = (String) msg.obj;
- if(str.contains("regist_ok"))
- Toast.makeText(RegisterActivity.this, "注册成功.", Toast.LENGTH_SHORT).show();
- else
- Toast.makeText(RegisterActivity.this, "服务器未开放.", Toast.LENGTH_SHORT).show();
- break;
- default:
- break;
- }
- };
- };
接下来我们来写服务器端:
服务器段用registerServlet处理客户端请求:registerServlet.java:
- package com.larson.pm;
- import java.io.IOException;
- import java.io.InputStream;
- import java.io.PrintWriter;
- import javax.servlet.ServletException;
- import javax.servlet.http.HttpServlet;
- import javax.servlet.http.HttpServletRequest;
- import javax.servlet.http.HttpServletResponse;
- import com.larson.tools.RegisterResultTool;
- public class RegisterServlet extends HttpServlet {
- public void doGet(HttpServletRequest request, HttpServletResponse response)
- throws ServletException, IOException {
- }
- public void doPost(HttpServletRequest request, HttpServletResponse response)
- throws ServletException, IOException {
- //1.获取输入输出流
- response.setContentType("text/html;charset=UTF-8");
- PrintWriter out = response.getWriter();
- InputStream in = request.getInputStream();
- //2.处理客户端发送的数据
- RegisterResultTool tool = new RegisterResultTool();
- String result = tool.register(in);
- //3.向客户端写相应数据
- out.write(result);
- out.flush();
- out.close();
- in.close();
- }
- }
servlet拿到客户端的数据inputStream,用一个工具类RegisterResultTool.java处理这些数据:
- package com.larson.tools;
- import java.io.InputStream;
- import javax.xml.parsers.SAXParserFactory;
- import org.xml.sax.InputSource;
- import org.xml.sax.XMLReader;
- import com.larson.bean.UserInfo;
- import com.larson.daoimpl.UserDao;
- import com.larson.handler.RegisterHandler;
- /**
- * 处理客户端发送过来数据的类
- *
- * @author Larson
- *
- */
- public class RegisterResultTool {
- /**
- * 处理客户端发送过来数据的类
- * @param in
- * 客户端的流
- * @return 处理结果
- */
- public String register(InputStream in) {
- String result = null;
- StringBuilder sb = new StringBuilder();
- //1.获取解析工厂
- SAXParserFactory factory = SAXParserFactory.newInstance();
- XMLReader reader= null;
- try {
- //2.自定义解析过程
- reader = factory.newSAXParser().getXMLReader();
- RegisterHandler handler = new RegisterHandler();
- reader.setContentHandler(handler);
- //3.开始解析客户端过来的输入流,并把数据封装到userInfo的bean中
- reader.parse(new InputSource(in));
- UserInfo user = handler.getUser();
- //4.往服务器的数据库添加一条用户信息
- UserDao dao = new UserDao();
- dao.add(user);
- //5.完成后给客户端反馈消息
- sb.append("<info>");
- sb.append("regist_ok");
- sb.append("</info>");
- } catch (Exception e) {
- //TODO 解析失败
- sb.append("<info>");
- sb.append("regist_fail");
- sb.append("</info>");
- e.printStackTrace();
- }
- result = sb.toString();
- return result;
- }
- }
再次过程中,我们需要自定义一个sax解析xml的handler对数据进行处理封装到bean文件中:
RegisterHandler.java:
- package com.larson.handler;
- import org.xml.sax.Attributes;
- import org.xml.sax.SAXException;
- import org.xml.sax.helpers.DefaultHandler;
- import com.larson.bean.UserInfo;
- public class RegisterHandler extends DefaultHandler {
- private UserInfo user;
- private String var="";
- @Override
- public void startElement(String uri, String localName, String qName,
- Attributes attributes) throws SAXException {
- //遇到user标签就表示是一个user对象
- if(qName.equals("user"))
- user = new UserInfo();
- super.startElement(uri, localName, qName, attributes);
- }
- @Override
- public void endElement(String uri, String localName, String qName)
- throws SAXException {
- if("username".equals(qName))
- user.setUsername(var);
- if("password".equals(qName))
- user.setPassword(var);
- if("nickname".equals(qName))
- user.setNickname(var);
- if("gender".equals(qName))
- user.setGender(var);
- //设置完临时属性置空
- var="";
- super.endElement(uri, localName, qName);
- }
- @Override
- public void characters(char[] ch, int start, int length)
- throws SAXException {
- var+=new String(ch, start, length);
- super.characters(ch, start, length);
- }
- /**
- * 获取填充完属性的user对象
- * @return
- */
- public UserInfo getUser() {
- return user;
- }
- }
,处理完毕以后,需要把这些数据写入到数据库,生成一条新的用户信息记录,因此需要些一个UserDao。,而我们习惯性用jdbcutils管理连接,这里为了代码可重用更好,我把所有修改的方法集合到一个update方法里面:JdbcUtils.java:
- package com.larson.tools;
- import java.io.InputStream;
- import java.sql.Connection;
- import java.sql.DriverManager;
- import java.sql.PreparedStatement;
- import java.sql.ResultSet;
- import java.sql.SQLException;
- import java.sql.Statement;
- import java.util.Properties;
- import com.larson.handler.ResultSetHandler;
- /**
- * 数据库相关
- * @author Larson
- *
- */
- public class JdbcUtils {
- // private static ComboPooledDataSource ds = null;
- private static Connection conn;
- static{
- try{
- InputStream in = JdbcUtils.class.getClassLoader().getResourceAsStream("db.properties");
- Properties properties = new Properties();
- properties.load(in);
- String url = properties.getProperty("url");
- String user = properties.getProperty("user");
- String passwd = properties.getProperty("password");
- String driver = properties.getProperty("driver");
- Class.forName(driver);
- conn = DriverManager.getConnection(url, user, passwd);
- // ds = new ComboPooledDataSource();
- // ds.setDriverClass(driver);
- // ds.setJdbcUrl(url);
- // ds.setUser(user);
- // ds.setPassword(passwd);
- //
- // ds.setInitialPoolSize(10);
- // ds.setMinPoolSize(5);
- // ds.setMaxPoolSize(20);
- //
- // ds = new ComboPooledDataSource();
- }catch (Exception e) {
- throw new ExceptionInInitializerError(e);
- }
- }
- /**
- * 获取连接
- * @return
- * @throws SQLException
- */
- public static Connection getConnection() throws SQLException{
- // return ds.getConnection();
- return conn;
- }
- /**
- * 释放连接
- * @param conn
- * @param st
- * @param rs
- */
- public static void release(Connection conn,Statement st,ResultSet rs){
- if(rs!=null){
- try{
- rs.close();
- }catch (Exception e) {
- e.printStackTrace();
- }
- rs = null;
- }
- if(st!=null){
- try{
- st.close();
- }catch (Exception e) {
- e.printStackTrace();
- }
- }
- if(conn!=null){
- try{
- conn.close();
- }catch (Exception e) {
- e.printStackTrace();
- }
- }
- }
- /**
- * 替换dao中的增删改方法
- * @param sql
- * @param params
- * @throws SQLException
- */
- public static void update(String sql,Object params[]) throws SQLException{
- Connection conn = null;
- PreparedStatement st = null;
- ResultSet rs = null;
- try{
- conn = getConnection();
- st = conn.prepareStatement(sql);
- for(int i=0;i<params.length;i++){
- st.setObject(i+1, params[i]);
- }
- st.executeUpdate();
- }finally{
- release(conn, st, rs);
- }
- }
- /**
- * 替换所有dao中的查询 策略模式
- * @param sql
- * @param params
- * @param rsh
- * @return
- * @throws SQLException
- */
- public static Object query(String sql,Object params[],ResultSetHandler rsh) throws SQLException{
- Connection conn = null;
- PreparedStatement st = null;
- ResultSet rs = null;
- try{
- conn = getConnection();
- st = conn.prepareStatement(sql);
- for(int i=0;i<params.length;i++){
- st.setObject(i+1, params[i]);
- }
- rs = st.executeQuery();
- return rsh.handler(rs);
- }finally{
- release(conn, st, rs);
- }
- }
- }
然后便是UserDao.java:
- package com.larson.daoimpl;
- import com.larson.bean.UserInfo;
- import com.larson.exception.DaoException;
- import com.larson.handler.BeanHandler;
- import com.larson.tools.JdbcUtils;
- public class UserDao {
- public void add(UserInfo user) {
- try {
- String sql = "insert into user(username,password,gender,nickname) values(?,?,?,?)";
- Object params[] = { user.getUsername(),
- user.getPassword(), user.getGender(),user.getNickname() };
- for(Object obj:params)
- System.out.println("userdao add---"+obj);
- JdbcUtils.update(sql, params);
- } catch (Exception e) {
- throw new DaoException(e);
- }
- }
- public void update(UserInfo user) {
- try {
- String sql = "update user set user=?,password=?,gender=?,nickname=? where id=?";
- Object params[] = { user.getId(), user.getUsername(),
- user.getPassword(), user.getNickname(), user.getId() };
- JdbcUtils.update(sql, params);
- } catch (Exception e) {
- throw new DaoException(e);
- }
- }
- public void delete(String id) {
- try {
- String sql = "delete from user where id=?";
- Object params[] = { id };
- JdbcUtils.update(sql, params);
- } catch (Exception e) {
- throw new DaoException(e);
- }
- }
- public UserInfo find(String id) {
- try {
- String sql = "select * from user where id=?";
- Object params[] = { id };
- return (UserInfo) JdbcUtils.query(sql, params, new BeanHandler(
- UserInfo.class));
- } catch (Exception e) {
- throw new DaoException(e);
- }
- }
- }
为了方便,我把bean文件也贴出来:
userInfo.java:
- package com.larson.bean;
- public class UserInfo {
- private int id;
- private String username;
- private String password;
- private String gender;
- private String nickname;
- public String getUsername() {
- return username;
- }
- public void setUsername(String username) {
- this.username = username;
- }
- public int getId() {
- return id;
- }
- public void setId(int id) {
- this.id = id;
- }
- public String getPassword() {
- return password;
- }
- public void setPassword(String password) {
- this.password = password;
- }
- public String getGender() {
- return gender;
- }
- public void setGender(String gender) {
- this.gender = gender;
- }
- public String getNickname() {
- return nickname;
- }
- public void setNickname(String nickname) {
- this.nickname = nickname;
- }
- }
本来准备用数据库连接池的,可是老是报错,就是上面注释的那几行,有懂的人麻烦告诉我,感激不尽。
让你的APP和你的服务器畅快通讯的更多相关文章
- web服务器、app(应用)服务器、DB后端性能瓶颈和分析
性能测试day07_性能瓶颈和分析 https://www.cnblogs.com/leixiaobai/p/9463748.html 其实如果之前都做的很到位的话,那么再加上APM工具(dynaTr ...
- TCP/IP协议学习(七) 基于C# Socket的Web服务器---动态通讯实现
目录 (1).基于Ajax的前端实现 (2).Web服务器后端处理 一个完整的web服务器,不仅需要满足用户端对于图片.文档等资源的需求:还能够对于用户端的动态请求,返回指定程序生成的数据.支持动态请 ...
- JavaWeb-SpringBoot(抖音)_二、服务器间通讯
JavaWeb-SpringBoot(抖音)_一.抖音项目制作 传送门 JavaWeb-SpringBoot(抖音)_二.服务器间通讯 传送门 JavaWeb-SpringBoot(抖音)_三.抖音项 ...
- App开发:模拟服务器数据接口 - MockApi
为了方便app开发过程中,不受服务器接口的限制,便于客户端功能的快速测试,可以在客户端实现一个模拟服务器数据接口的MockApi模块.本篇文章就尝试为使用gradle的android项目设计实现Moc ...
- 27.app后端搭建聊天服务器的经历
现在,聊天功能已经成了社交app的标配了.但是,众多web开发出生的程序员对聊天相关的服务的不了解,带来了很多开发上的困扰.在这篇文章中,根据下面3个方面,谈谈聊天服务. 1. 聊天服务的技 ...
- 9.app后端选择什么服务器
对于很多刚入行的朋友来说,不清楚应该选择什么样的服务器提供商,是选择传统的IDC, 租用服务器租用机柜,还是选择现在很火的云服务器呢?在本文中,通过对比传统的IDC和云服务,简单阐述一下服务器的选择. ...
- iOS 开发App捕获异常, 反馈给服务器, 提高用户体验
在我们开发的app中, 不可避免的, 有时候用户使用软件会崩溃. 我们就需要捕获异常, 可以在入口类中加入相应的代码, 可以在每次用户打开程序的时候, 检查一下沙盒中是否有崩溃日志, 如果有, 可以 ...
- app页面连接到服务器的数据库
第一步在服务器上写好servlet用于和数据库交互,目前我只写了添加. 第二步app端使用HttpURLConnection连接交互. 效果图: 增加了一条数据:第十一条
- 使用h5开发跨平台APP确保数据安全交互---服务器篇
从eclipse到android studio的安卓开发经验告诉我原声开发才是硬道理,其实以前很抵触html5开发app的,虽然没有去了解过,但是冥冥中就觉得它运行速度太慢了,加载渲染根本比不上原生开 ...
随机推荐
- 应用Flume+HBase采集和存储日志数据
1. 在本方案中,我们要将数据存储到HBase中,所以使用flume中提供的hbase sink,同时,为了清洗转换日志数据,我们实现自己的AsyncHbaseEventSerializer. pac ...
- Java开发牛人十大必备网站
以下是我收集的Java开发牛人必备的网站.这些网站可以提供信息,以及一些很棒的讲座, 还能解答一般问题.面试问题等.质量是衡量一个网站的关键因素,我个人认为这些网站质量都很好.接下来,我会跟大家分享我 ...
- 数据库实例: STOREBOOK > 表空间
ylbtech-Oracle:数据库实例: STOREBOOK > 表空间 表空间(默认) 1. 表空间(默认)返回顶部 1.1, 1.2, 2. 表空间列表(默认)返回顶部 2.1, SYSA ...
- 3D几何图形的生成算法
在之前的博客上,发布了一个我写的3D几何图形生成的DEMO: http://www.cnblogs.com/WhyEngine/p/3415040.html DEMO下载地址: http://file ...
- [置顶] Java中字符串为什么不以\0结尾
其实这个问题没有什么好说的,Java里面一切都是对象,是对象的话,字符串肯定就有长度,即然有长度,编译器就可以确定要输出的字符个数,当然也就没有必要去浪费那1字节的空间用以标明字符串的结束了. 学过C ...
- RAID5工作原理介绍
RAID 5是一种存储性能.数据安全和存储成本兼顾的存储解决方案.以四个硬盘组成的RAID 5为例,其数据存储方式如图4所示:图中,P0为D0,D1和D2的奇偶校验信息,P1为D3,D4,D5的奇偶校 ...
- Endv 博客简介
Endv 博客简介 此博客收集了 C++.Android.C#.java.php 等优秀的开源项目, 同时也对 Windows.Linux.CentOS 等系列操作系统的开发环境.办公环境的配置写了一 ...
- Thread-Local Storage for C99
线程本地存储(TLS)是一种机制,通过这样的机制进行变量分配.在每一个现存线程都有一个实例变量.这样的执行模型GCC用来实现这个,起源于IA-64处理器,可是已经被迁移到其它的处理器.它须要大量的支持 ...
- js的正则匹配 和 blur
<script type="text/javascript" src="http://code.jquery.com/jquery-1.10.2.min.js&qu ...
- Discuz常见小问题-如何实现word文档转成帖子
有一些网站比如QQ空间是可以直接导入Word文件生成网页版本的,但是效果不理想 可以发现图片进来之后都是变形了的 最笨的方法是一个一个复制粘贴(当然也不需要这么麻烦,你可以打开一个word文档之后,保 ...