JDBC实例之—手机号码归属地查询(控制台版本)

JDBC实例之—手机号码归属地查询(控制台版本)

JDBC基础入门学习小练习,实现控制台提示输入电话号码,输入完成回册后,打印电话号码归属地和运营商类型。
实现步骤
1. 编写手机号码归属地数据库文件解析程序,从文件中获得有效的字段(号码段对应的地区和运营商类型)。
2. 在mysql数据库中创建表(Table),采用Navicat Lite来创建表。
3. 将从数据库文件中解析出来字段按格式插入到mysql的表中,采用批量的方式来插,不然耗时太久。
4. 编写控制台程序,用于和用户交互读取输入的电话号码,并提取出前7位,在mysql查询结果集中进行遍历,如果查询到,则获取该行的地区和运营商类型,然后输出,如果没有查询到输出“未知号码”。

1.  查询功能实现,在查询之前,数据库中的表已经插入了数据了。 主程序代码:
import java.util.*;
import java.sql.*;

/**
 * 	主程序,完成控制台输入,数据查询,遍历比较,控制台输出
 * */
public class PhoneNumberQuery
{

	public static void main(String[] args)
	{
		//控制台输入
		Scanner in = new Scanner(System.in);		
		String inPhoneNumber = null;	//输入的电话号码
		
		//输出
		String strPhoneNumber = null;
		String strArea = null;			//输出号码归属地
		String strMobileType = null;	//输出运营商类型
		
		//SQL查询语句
		String sql = "Select * from T_PhoneNumber";
		
		//创建数据库连接
		Connection conn 	 = null;
		PreparedStatement ps = null;
		ResultSet rs 		 = null;
		
		//执行SQL查询
		try
		{
			conn = JdbcUtils.getConnection();	//获得连接
			ps   = conn.prepareStatement(sql);	//获得预编译的 SQL语句的对象
			rs   = ps.executeQuery();			//获得查询结果集
			
			while(true)
			{
				System.out.print("请输入电话号码:");
				
				//获取输入的电话号码,提取前7位
				inPhoneNumber = in.nextLine();			
				inPhoneNumber = inPhoneNumber.substring(0, 7);
				
				//从第一行开始遍历直到查询成功,或者遍历到最后一行
				while(rs.next())
				{
					//从数据库查询结果集中获取电话号码前7位
					strPhoneNumber = rs.getString("PhonePrefix");
					//逐条和输入电话号码进行比较
					if(strPhoneNumber.equals(inPhoneNumber))
					{
						//查询成功,获取地区和运营商类型字段
						strArea = rs.getString("Area");
						strMobileType = rs.getString("MobileType");
						//退出遍历
						break;
					}
				}
				//如果查旬结果为空
				if(strArea == null && strMobileType == null)
				{
					System.out.println("未知号码");
				}
				else
				{
					//查询成功输出信息
					System.out.print(strArea + "   ");	
					System.out.println(strMobileType);	
				}
				//变量归零,进行下一次查询
				strArea       = null;
				strMobileType = null;
				inPhoneNumber = null;
				rs.first();				//将结果集返回到第一行
			}			
		}
		catch(SQLException e)
		{
			e.printStackTrace();
		}
		finally
		{
			//资源关闭
			JdbcUtils.closeQuietly(rs);
			JdbcUtils.closeQuietly(ps);
			JdbcUtils.closeQuietly(conn);
			
			in.close();
		}
	}
}

运行效果:


2.  号码归属地数据库文件解析功能实现
    实际上,在进行主程序查询前,已经创建了数据表,并插入了号码归属地数据,号码归属地文件解析,信息提取,批量插入等功能放在PhoneNumberPrase.java中,数据表创建的数据插入只需执行一次,则该表以后要以多次利用,所以这是一个单独的应用程序,实现代码如下:
import java.io.*;
import java.sql.*;


/**
 * 		解析号码归属地csv文件,提取有效信息,插入数据表中
 * 
 * */

/**
 * 号码归属地解析类,实现.CSV文件内容的解析,并插入到mysql数据中
 * @author  樊文杰
 * @version V0.1
 * */
public class PhoneNumberPrase
{
	public  static InputStream csvFile = null;
	public  static InputStreamReader csvFileReader = null;
	public  static BufferedReader csvFileBufferReader = null;
	
	/**
	 * 号码归属地数据源文件读取,返回输入流
	 * @param	filePath csv文件源路径
	 * @return  文件流
	 * */
	public static BufferedReader getCsvFileBuffer(String filePath) throws IOException
	{
        //字节读——>字符读——>缓冲读(行读)
    	csvFile = new FileInputStream(filePath);
    	csvFileReader = new InputStreamReader(csvFile);
    	csvFileBufferReader = new BufferedReader(csvFileReader);
        
        return csvFileBufferReader;
	}
	
	
	public static void main(String[] args) throws SQLException 
	{
		BufferedReader csvFileBuffer = null;
		String line = null;
		int count = 0;
		
		//数据库连接和SQL语句预编译对像
		Connection conn = null;
		PreparedStatement pstmt = null;
		
		//计算插入用时
		long start = System.currentTimeMillis();
		
		try
		{
			//从当前工作空间的src目录下读取数据文件
			csvFileBuffer = getCsvFileBuffer("./src/PhoneNumbersDataBase.csv");
			//丢弃第一行数据
			csvFileBuffer.readLine();
			
			//创建数据 连接,关闭连接默认的自动提交功能
			conn = JdbcUtils.getConnection();
			conn.setAutoCommit(false);			//关闭自动提交
			//获取SQL语句预编译的对像
			pstmt = conn.prepareStatement("Insert into T_PhoneNumber(PhonePrefix,Area,MobileType) values(?,?,?)");
			
			//读取CSV数据行,每2000行提交一次
			while( (line = csvFileBuffer.readLine()) != null)
			{
				//分解一行字符串,然后进行处理得到有效数据
				String[] segments = line.split(",");
				String phonePrefix = segments[1].replace("\"", "");
				String area = segments[2].replace("\"", "");
				String yys  = segments[3].replace("\"", "");
				
				//清空参数集
				pstmt.clearParameters();
				//赋值
				pstmt.setString(1, phonePrefix);
				pstmt.setString(2, area);
				pstmt.setString(3, yys);
				pstmt.addBatch();
				
				count ++;
				
				//2000行批量更新一次
				if(count%2000 == 0)
				{
					pstmt.executeBatch();
				}
				//System.out.printf("号码前缀:%s, %s, %s\n",phonePrefix,area,yys);
			}
			//得交剩余不足2000行的部分
			pstmt.executeBatch();
			//事物提交
			conn.commit();
			
			//结整时间,计算此过程用时
			long end = System.currentTimeMillis();
			System.out.println("执行成功,用时: " + (end - start) + " ms");
		} 
		catch (IOException e)
		{
			// TODO 自动生成的 catch 块
			e.printStackTrace();
		}
		catch (SQLException e)
		{
			//如果事物提交出错,则进行回滚
			conn.rollback();
			e.printStackTrace();
		}
		finally
		{
			//关闭资源,包括:IO流,JDBC的连接等
			IOUtils.closeQuietly(csvFileBuffer);
			JdbcUtils.closeQuietly(pstmt);
			JdbcUtils.closeQuietly(conn);
	
		}
	}
}

3. 数据表插入实现,    JDBC常用功能封装,包括: 加载驱动,创建连接,执行SQL语句并更新,查询结果集等,代码封装如下:

import java.io.*;

import java.sql.Connection;
import java.sql.DriverManager;
import java.sql.Statement;
import java.sql.PreparedStatement;
import java.sql.SQLException;
import java.sql.ResultSet;
import java.util.Properties;

/**
 * JAVA JDBC常用功能封装
 * @author 樊文杰
 * @version V0.1
 * */
public class JdbcUtils
{
	public static String driverName = null;
	public static String dbUrl      = null;
	public static String dbUserName = null;
	public static String dbPassWord = null;
	
	/**
	 * 静态代码块,加载配置文件JdbcConfig.properties,读取MySQL配置信息,
	 * 然后加载驱动程序
	 * 
	 * */
	static{
		
		InputStream inStream = null;
		
		// 1.加载配置文件
		try
		{			
    		inStream = JdbcUtils.class.getResourceAsStream("JdbcConfig.properties");
    		
    		Properties props = new Properties();
    		props.load(inStream);
    		
    		//提取配置文件中的相关字段
    		driverName = props.getProperty("drivername");
    		dbUrl	   = props.getProperty("dburl");
    		dbUserName = props.getProperty("dbusername");
    		dbPassWord = props.getProperty("dbpassword");
		}
		catch(IOException e)
		{
			throw new RuntimeException("加载JdbcConfig.properties出错",e);
		}
		finally{
			
			if(inStream != null)
			{				
				try
				{
					inStream.close();
				}
				catch(IOException e)
				{
					
				}
			}
		}
		
		//2.加载驱动程序,驱动程序名由配置文件解析得到
		try
		{
			Class.forName(driverName);			
		}
		catch(ClassNotFoundException e)
		{
			System.out.println("驱动加载出错:" + e.getMessage());
		}		
	}
	
	/**
	 * 创建与数据库的连接
	 * @return 返回的连接
	 * */
	public static Connection getConnection() throws SQLException
	{
		return DriverManager.getConnection(dbUrl,dbUserName,dbPassWord);
	}
		
	/**
	 * 在指定的连接上执行SQL语句并更新结果
	 * @param conn 指定的连接
	 * @param sql  SQL语句
	 * @param parameters 可变参数列表
	 * @return 返回更新的条目
	 */
	public static int executeUpdate(Connection conn, String sql, Object ...parameters)
	{		
		PreparedStatement ps = null;
		
		try
		{
			//获得SQL语句预编译的结果存储对像
			ps = conn.prepareStatement(sql);
			for(int i = 0; i < parameters.length; i ++)
			{
				ps.setObject(i+1, parameters[i]);
			}		
			return ps.executeUpdate();	
		}
		catch(SQLException e)
		{
			System.out.println(e);
		}
		finally
		{
			closeQuietly(ps);
		}
		
		return -1;
	}
	
	/**
	 * 执行SQL语句并更新结果
	 * @param sql  SQL语句
	 * @param parameters 可变参数列表
	 * @return 返回更新的条目
	 */
	public static int executeUpdate(String sql, Object ...parameters)
	{
		Connection conn = null;
		
		//首先创建连接,然后再执行SQL语句
		try
		{
			conn = getConnection();	
			return executeUpdate(conn,sql,parameters);
		}
		catch(SQLException e)
		{
			System.out.println(e);
		}
		finally
		{
			closeQuietly(conn);
		}
		
		return 0;
	}
	
	/**
	 * 在指定的连接上执行SQL查询并返回结果集
	 * @param conn 指定的连接
	 * @param sql  SQL语句
	 * @param parameters 可变参数列表
	 * @return 返回结果集
	 */
	public static ResultSet executeQuery(Connection conn,String sql,
										 Object ...parameters) throws SQLException
	{
		//获取连接上SQL语句预编译对像
		PreparedStatement ps = conn.prepareStatement(sql);
		
		for(int i = 0; i < parameters.length; i ++)
		{
			ps.setObject(i+1, parameters[i]);
		}
		
		//执行查询
		return ps.executeQuery();
	}
	
	
	public static ResultSet executeQuery(String sql, Object ...parameters)
										 throws SQLException
	{
		Connection conn = getConnection();
		return executeQuery(conn,sql,parameters);
	}
		

	//关闭资源方法封装
	public static void closeQuietly(ResultSet res)
	{
		if(res != null)
		{
			try{
				res.close();
			}
			catch(SQLException e)
			{
				// do nothing
			}
		}
	}

	public static void closeQuietly(Connection conn)
	{
		if(conn != null)
		{
			try{
				conn.close();
			}
			catch(SQLException e)
			{
				// do nothing
			}
		}
	}
	
	public static void closeQuietly(Statement stmt)
	{
		if(stmt != null)
		{
			try{
				stmt.close();
			}
			catch(SQLException e)
			{
				// do nothing
			}
		}
	}
	
	public static void closeAll(ResultSet rs)
	{
		try
		{
			if(rs != null)
			{
				closeQuietly(rs.getStatement().getConnection());
				closeQuietly(rs.getStatement());
				closeQuietly(rs);
			}
		}
		catch(SQLException e)
		{
			
		}
	}

}


  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值