一、springIOC

控制反转和依赖注入

​ 简单的说就是将对象的创建,属性的的设置交给spring容器进行管理,而不再由用户自己创建,当用户需要使用该接口或者类的时候,直接注入就可以了,spring容器会自动帮助用户创建对象。

1.创建maven应用程序

【pom.xml】

​ 1.引入spring依赖,junit依赖

​ 2.引入maven插件——java编译插件

  1. <project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
  2. xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
  3. <modelVersion>4.0.0</modelVersion>
  4. <groupId>com.itcloud</groupId>
  5. <artifactId>resource</artifactId>
  6. <version>1.0-SNAPSHOT</version>
  7. <packaging>jar</packaging>
  8. <name>resource</name>
  9. <url>http://maven.apache.org</url>
  10. <properties>
  11. <project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
  12. </properties>
  13. <dependencies>
  14. <dependency>
  15. <groupId>org.springframework</groupId>
  16. <artifactId>spring-context</artifactId>
  17. <version>4.3.15.RELEASE</version>
  18. </dependency>
  19. <dependency>
  20. <groupId>junit</groupId>
  21. <artifactId>junit</artifactId>
  22. <version>4.12</version>
  23. <scope>test</scope>
  24. </dependency>
  25. </dependencies>
  26. <build>
  27. <plugins>
  28. <plugin>
  29. <groupId>org.apache.maven.plugins</groupId>
  30. <artifactId>maven-compiler-plugin</artifactId>
  31. <version>3.7.0</version>
  32. <configuration>
  33. <source>1.8</source>
  34. <target>1.8</target>
  35. <encoding>UTF-8</encoding>
  36. </configuration>
  37. </plugin>
  38. </plugins>
  39. </build>
  40. </project>

该依赖会下载下面jar

  1. <groupId>org.springframework</groupId>
  2. <artifactId>spring-context</artifactId>
  • org.springframework:spring-aop:4.3.15.RELEASE
  • org.springframework:spring-beans:4.3.15.RELEASE
  • org.springframework:spring-core:4.3.15.RELEASE
  • org.springframework:spring-expression:4.3.15.RELEASE

2.springIOC基础

基本概念:springIOC主要作用是用来管理javaBean的容器,将java对象以及对象和对象之间的关系交由Spring容器管理。

在没有spring容器之前对接口或者类进行实例化的时候都需要使用new关键字,来进行对象的创建,那么自从有了spring,那么这些事情就交给了spring来做了。

2.1.了解spring的几种注入方式

【Teacher.java】

​ getter和setter方法在这里都会被省略。

一个老师对应多个学生,老师pojo类中包含setter注入,和List集合注入

  1. public class Teacher implements Serializable {
  2. private Long id;
  3. private String name;
  4. private Integer age;
  5. private List<Student> students;
  6. }

【Student.java】

一个学生对应一个老师,学生包含多种注入方式,有setter,Properties类注入,map注入以及构造方法注入

注意点,

​ 1.如果添加了有参构造方法(没有参构造),那么在进行注入的时候必须要进行构造方法的注入

​ 2.如果既有有参构造和无参构造可以不进行构造方法的注入

  1. public class Student implements Serializable {
  2. private Long id;
  3. private String name;
  4. private Teacher teacher;
  5. private Properties pro;
  6. private Map<String,Object> map;
  7. public Student(){}
  8. public Student(Long id, String name){
  9. this.id = id;
  10. this.name = name;
  11. }
  12. }

【applicationContext.xml】**创建spring容器

  1. <?xml version="1.0" encoding="UTF-8"?>
  2. <beans xmlns="http://www.springframework.org/schema/beans"
  3. xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
  4. xsi:schemaLocation="http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans.xsd">
  5. <bean id="student" class="com.itcloud.pojo.Student">
  6. <property name="id" value="1"/>
  7. <property name="name" value="小明"/>
  8. </bean>
  9. <bean id="student2" class="com.itcloud.pojo.Student">
  10. <!-- 构造方法注入 -->
  11. <!--每一个标签都代表一个构造方法的属性,按照参数在构造方法中的顺序进行注入-->
  12. <constructor-arg value="2"/>
  13. <constructor-arg>
  14. <value>张三</value>
  15. </constructor-arg>
  16. <property name="teacher" ref="teacher" />
  17. <!-- map注入 -->
  18. <property name="map">
  19. <map>
  20. <entry key="1" value="语文" />
  21. <entry key="2" value="数学" />
  22. </map>
  23. </property>
  24. <!-- Properties注入 -->
  25. <property name="pro">
  26. <props>
  27. <prop key="身高">1.8</prop>
  28. <prop key="体重">70kg</prop>
  29. </props>
  30. </property>
  31. </bean>
  32. <bean id="teacher" class="com.itcloud.pojo.Teacher">
  33. <property name="id" value="100023" />
  34. <property name="name" value="王老师" />
  35. <property name="age" value="30" />
  36. <!-- list集合注入 -->
  37. <property name="students">
  38. <list>
  39. <ref bean="student2" />
  40. <ref bean="student" />
  41. </list>
  42. </property>
  43. </bean>
  44. </beans>

【TestIOC.java】进行数据的测试,debug观察数据

  1. package com.itcloud.pojo;
  2. import org.junit.Test;
  3. import org.springframework.context.ApplicationContext;
  4. import org.springframework.context.support.ClassPathXmlApplicationContext;
  5. public class TestIOC {
  6. //加载spring容器
  7. private ApplicationContext context =
  8. new ClassPathXmlApplicationContext("classpath:spring/applicationContext.xml");
  9. @Test
  10. public void testStudent() {
  11. //context.getBean()获取spring容器中管理的bean,参数为Id
  12. Student stu1 = (Student) context.getBean("student");
  13. Student stu2 = context.getBean("student2", Student.class);
  14. Teacher teacher = context.getBean("teacher", Teacher.class);
  15. System.out.println("---------------------");
  16. }
  17. }
2.2.p标签和c标签的注入方式

​ p代表的就是属性,c代表的就是构造方法。

添加标签头,引入p和c

  1. xmlns:p="http://www.springframework.org/schema/p"
  2. xmlns:c="http://www.springframework.org/schema/c"

实例

c:id="3" c:name="smith"就是构造方法中的两个参数 id和name,p:teacher-ref="teacher"为类中中的属性teacher

  1. <bean id="student3" class="com.itcloud.pojo.Student" c:id="3" c:name="smith" p:teacher-ref="teacher"/>
2.3.bean之间的继承关系

两个关键字段parentabstract

1.此时student3会继承student中的id,和name属性,这个是parent的作用,非必须标签

2.abstract表示student这个bean无法被实例化,即无法再代码中获取这个bean,也无法被外部所引用,非必须标签

​ 例如:ref="student"是错的

  1. <bean id="student" class="com.itcloud.pojo.Student" abstract="true">
  2. <property name="id" value="1"/>
  3. <property name="name" value="小明"/>
  4. </bean>
  5. <bean id="student3" class="com.itcloud.pojo.Student" parent="student" p:teacher-ref="teacher"/>
2.4.bean的作用域

概述

作用域 描述
单例(singleton) (默认)每一个Spring IoC容器都拥有唯一的一个实例对象
原型(prototype) 一个Bean定义,任意多个对象

scope="singleton"默认值,只会产生一个实例化对象

scope="prototype"原型,每次获取bean的时候都会获取一个新的实例化对象

  1. <bean id="student4" class="com.itcloud.pojo.Student" parent="student" p:teacher-ref="teacher" scope="singleton"/>
2.6.bean的生命周期

两个关键点:

​ 1.<bean/>标签中的字段:init-method=""表示bean初始化(构造方法)之后调用的方法 destroy-method=""容器关闭之后调用的方法.

​ 2. bean的后置处理器,需要实现方法,BeanPostProcessor这个类,两个方法:

postProcessBeforeInitialization():在每个bean初始化后(构造方法)调用一次(在init-method方法之前被调用)。

postProcessAfterInitialization():在init-method之后被调用,destroy-method之前被调用

实现案例0001

【LifeCycle.java】

  1. package com.itcloud.pojo;
  2. public class LifeCycle {
  3. public LifeCycle(){
  4. System.out.println("构造方法初始化..........");
  5. }
  6. public void init(){
  7. System.out.println("init()初始化方法.......");
  8. }
  9. public void destory(){
  10. System.out.println("destory()销毁方法.......");
  11. }
  12. }

【applicationContext.xml】

init-method="init" destroy-method="destory"

  1. <bean id="lifeCycle" class="com.itcloud.pojo.LifeCycle" init-method="init" destroy-method="destory"></bean>

【TestIOC.java】测试

  1. public class TestIOC {
  2. //加载spring容器
  3. private ClassPathXmlApplicationContext context =
  4. new ClassPathXmlApplicationContext("classpath:spring/applicationContext.xml");
  5. @Test
  6. public void testStudent() {
  7. LifeCycle lifeCycle = context.getBean("lifeCycle", LifeCycle.class);
  8. context.close();
  9. //测试结果
  10. /*
  11. 信息: Loading XML bean definitions from class path resource [spring/applicationContext.xml]
  12. 构造方法初始化..........
  13. init()初始化方法.......
  14. 四月 08, 2018 10:09:34 上午 org.springframework.context.support.ClassPathXmlApplicationContext doClose
  15. 信息: Closing org.springframework.context.support.ClassPathXmlApplicationContext@27ddd392: startup date [Sun Apr 08 10:09:33 CST 2018]; root of context hierarchy
  16. destroy()销毁方法.......
  17. */
  18. }
  19. }

第二个关键点实现案例0002

【CycleProcessor.java】

  1. package com.itcloud.pojo;
  2. import org.springframework.beans.BeansException;
  3. import org.springframework.beans.factory.config.BeanPostProcessor;
  4. import org.springframework.stereotype.Component;
  5. public class CycleProcessor implements BeanPostProcessor {
  6. @Override
  7. public Object postProcessBeforeInitialization(Object bean, String name) throws BeansException {
  8. System.out.println("CycleProcessor start....." + name);
  9. return bean;
  10. }
  11. @Override
  12. public Object postProcessAfterInitialization(Object bean, String name) throws BeansException {
  13. System.out.println("CycleProcessor end....." + name);
  14. return bean;
  15. }
  16. }

【TestIOC.java】测试类不变,测试结果:

  1. /*
  2. 构造方法初始化..........
  3. CycleProcessor start.....lifeCycle
  4. init()初始化方法.......
  5. CycleProcessor end.....lifeCycle
  6. 四月 08, 2018 10:13:31 上午 org.springframework.context.support.ClassPathXmlApplicationContext doClose
  7. 信息: Closing org.springframework.context.support.ClassPathXmlApplicationContext@58c1670b: startup date [Sun Apr 08 10:13:00 CST 2018]; root of context hierarchy
  8. destroy()销毁方法.......
  9. */
2.7.工厂注入(了解即可)

注意点,如果工厂方法有参数,通过<constructor-arg value="xxx"></constructor-arg>进行参数匹配

静态工厂注入

  1. public class StudentFactory {
  2. public static Student getInstance(){
  3. Student stu = new Student();
  4. stu.setId(10L);
  5. stu.setName("小十");
  6. return stu;
  7. }
  8. }
  1. <bean id="student6" class="com.itcloud.pojo.StudentFactory" factory-method="getInstance"></bean>

测试

  1. Student stu = context.getBean("student6", Student.class);

实例工厂注入

  1. package com.itcloud.pojo;
  2. public class TeacherFactory {
  3. public Teacher getInstance(Long id, String name){
  4. Teacher teacher = new Teacher();
  5. teacher.setId(id);
  6. teacher.setName(name);
  7. return teacher;
  8. }
  9. }
  1. <!-- 实例工厂必须单独配置一个bean -->
  2. <bean id="teacherFactory" class="com.itcloud.pojo.TeacherFactory"/>
  3. <bean id="teacher2" factory-bean="teacherFactory" factory-method="getInstance">
  4. <constructor-arg>
  5. <value>222</value>
  6. </constructor-arg>
  7. <constructor-arg name="name" value="张老师" />
  8. </bean>

测试

  1. Teacher teacher = context.getBean("teacher2", Teacher.class);

FactoryBean配置

跳转标志

  1. package com.itcloud.pojo;
  2. import org.springframework.beans.factory.FactoryBean;
  3. public class TeacherFactoryBean implements FactoryBean {
  4. private String name;
  5. @Override
  6. public Object getObject() throws Exception {
  7. Teacher teacher = new Teacher();
  8. teacher.setName(name);
  9. return teacher;
  10. }
  11. @Override
  12. public Class<?> getObjectType() {
  13. return Teacher.class;
  14. }
  15. @Override
  16. public boolean isSingleton() {
  17. return true;
  18. }
  19. public void setName(String name) {
  20. this.name = name;
  21. }
  22. }
  1. <!--FactoryBean方法配置bean-->
  2. <bean id="teacherBean" class="com.itcloud.pojo.TeacherFactoryBean">
  3. <property name="name" value="李老师"/>
  4. </bean>
  1. Teacher teacher = context.getBean("teacherBean", Teacher.class);

3.spring注解注入

​ 三个注解将类注入到spring容器中,注意点:注解默认注入的Id为当前类的名称首字母小写

  • @Repository主要用于dao,数据访问层
  • @Service用于Service层,调用数据访问层的方法,进行逻辑操作
  • @Component用户普通类的注册,用户自己定义的组件

我们知道Service层一定会调用dao层的相关方法,dao层已经被注册到Spring容器之中,这是后就需要使用Spring为我们提供的注解来引用对应的实例

  • @Autowired按照类型进行匹配,如果一个接口存在两个子类,可以配合@Qualifier注解来使用
  • @Resource按照名称进行匹配,
3.1简单应用应用案例

【applicationContext-annotation.xml】支持注解配置

  1. <?xml version="1.0" encoding="UTF-8"?>
  2. <beans xmlns="http://www.springframework.org/schema/beans"
  3. xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
  4. xmlns:p="http://www.springframework.org/schema/p"
  5. xmlns:c="http://www.springframework.org/schema/c" xmlns:context="http://www.springframework.org/schema/context"
  6. xsi:schemaLocation="http://www.springframework.org/schema/beans
  7. http://www.springframework.org/schema/beans/spring-beans.xsd http://www.springframework.org/schema/context http://www.springframework.org/schema/context/spring-context.xsd">
  8. <!-- 此配置表示com.itcloud包及其子包支持注解配置 -->
  9. <context:component-scan base-package="com.itcloud">
  10. </context:component-scan>
  11. </beans>

【UserDAO.java】

  1. package com.itcloud.dao;
  2. public interface UserDAO {
  3. //用户更新
  4. int update();
  5. }

【UserDAOImpl.java】注意点:@Repository的value的值默认是(userDAOImpl)

  1. @Repository
  2. public class UserDAOImpl implements UserDAO {
  3. @Override
  4. public int update() {
  5. System.out.println("进行数据库语句编写");
  6. return 0;
  7. }
  8. }

【UserService.java】

  1. package com.itcloud.service;
  2. public interface UserService {
  3. int doUpdate();
  4. }

【UserServiceImpl.java】@Service的value的默认值是:userServiceImpl

  1. ackage com.itcloud.service.impl;
  2. import com.itcloud.dao.UserDAO;
  3. import com.itcloud.service.UserService;
  4. import org.springframework.beans.factory.annotation.Autowired;
  5. import org.springframework.stereotype.Service;
  6. @Service
  7. public class UserServiceImpl implements UserService {
  8. @Autowired
  9. private UserDAO userDAO;
  10. @Override
  11. public int doUpdate() {
  12. System.out.println("UserServiceImpl update()方法开始....");
  13. userDAO.update();
  14. return 0;
  15. }
  16. }

测试

  1. context.getBean("userDAOImpl");//结果:userDAOImpl@127 即:获取到UserDAO的对象

理解bean之间的相互调用

我们在UserServiceImpl这个类中可以看到如下这句话,这句话表示的意思就是引用外部bean,在没有Spring之前我们引入外部bean的过程是:private UserDAO userDAO = new UserDAOImpl(),在有了Spring之后,spring会自动帮我们进行对象的创建,以及维护对象之间的关系。

  1. @Autowired
  2. private UserDAO userDAO;

测试Autowired

  1. @Test
  2. public void testAnnotation(){
  3. UserService userService = context.getBean(UserService.class);
  4. userService.doUpdate();
  5. }
  6. //结果
  7. /*
  8. UserServiceImpl update()方法开始....
  9. 进行数据库语句编写
  10. */

前面提到,@Autowired是根据类型进行注入的,此时因为UserDAO只有一个子类,但是如果有两个子类要怎么书写呢:

  1. //方案一,官方推荐
  2. @Autowired
  3. @Qualifier("userDAOImpl")
  4. private UserDAO userDAO;
  5. //方案二
  6. @Resource(name = "userDAOImpl")
  7. private UserDAO userDAO;
  8. //或者
  9. @Resource
  10. private UserDAO userDAOImpl;
3.2理解开启注解支持配置

【applicationContext-annotation.xml】

  1. <context:component-scan base-package="com.itcloud">
  2. </context:component-scan>

这里也可以添加子元素,对注解数据进行过滤

最常用的过滤方式

  1. <context:component-scan base-package="com.itcloud" use-default-filters="false">
  2. <!--只包含Service注解的bean,其他注解不会被扫描-->
  3. <context:include-filter type="annotation" expression="org.springframework.stereotype.Service"/>
  4. </context:component-scan>

use-default-filters="false"不使用默认过滤方式,如果为true的话,<context:include-filter type="annotation" expression="org.springframework.stereotype.Service"/> 表示的意思只是将@Service包含进来,其他注解也会包含的

  1. <!--表示不扫描Repository注解-->
  2. <context:exclude-filter type="annotation" expression="org.springframework.stereotype.Repository"/>

4.spring引用外部属性文件

4.1 applicationContext.xml文件配置bean并且注入属性文件中的内容

【value.properties】定义一个外部属性文件

  1. value.driverName=com.mysql.jdbc.Driver
  2. value.url=jdbc:mysql://localhost:3306/test
  3. value.username=root
  4. value.password=123456

【DataSource.java】定义属性类

  1. package com.itcloud.value;
  2. public class DataSource {
  3. private String driverName;
  4. private String username;
  5. private String password;
  6. private String url;
  7. //getter setter方法略
  8. }

【applicationContext-annotation.xml】在spring配置文件中获取属性文件内容

  1. <?xml version="1.0" encoding="UTF-8"?>
  2. <beans xmlns="http://www.springframework.org/schema/beans"
  3. xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
  4. xmlns:p="http://www.springframework.org/schema/p"
  5. xmlns:c="http://www.springframework.org/schema/c" xmlns:context="http://www.springframework.org/schema/context"
  6. xsi:schemaLocation="http://www.springframework.org/schema/beans
  7. http://www.springframework.org/schema/beans/spring-beans.xsd http://www.springframework.org/schema/context http://www.springframework.org/schema/context/spring-context.xsd">
  8. <context:property-placeholder location="classpath:properties/value.properties"/>
  9. <bean id="dataSource" class="com.itcloud.value.DataSource">
  10. <property name="username" value="${value.username}"/>
  11. <property name="password" value="${value.password}"/>
  12. <property name="driverName" value="${value.driverName}"/>
  13. <property name="url" value="${value.url}"/>
  14. </bean>
  15. </beans>

此时,当spring容器加载的时候,DataSource.java 被实例化, value.properties属性文件中的内容会被注入到DataSource中。

4.2不通过配置文件的方式读取属性

【applicationContext-annotation.xml】开启注解配置

  1. <context:component-scan base-package="com.itcloud"/>
  2. <context:property-placeholder location="classpath:properties/value.properties"/>
  3. <!--<bean id="dataSource" class="com.itcloud.value.DataSource">-->
  4. <!--<property name="username" value="${value.username}"/>-->
  5. <!--<property name="password" value="${value.password}"/>-->
  6. <!--<property name="driverName" value="${value.driverName}"/>-->
  7. <!--<property name="url" value="${value.url}"/>-->
  8. <!--</bean>-->

【DataSource.java】 此时可以没有setter方法

  1. package com.itcloud.value;
  2. import org.springframework.beans.factory.annotation.Value;
  3. import org.springframework.stereotype.Component;
  4. @Component
  5. public class DataSource {
  6. @Value("${value.driverName}")
  7. private String driverName;
  8. @Value("${value.username}")
  9. private String username;
  10. @Value("${value.password}")
  11. private String password;
  12. @Value("${value.url}")
  13. private String url;
  14. }

三、spring成长之路——springIOC容器详解(上)的更多相关文章

  1. 四、spring成长之路——springIOC容器(下)

    目录 5.spring注解开发(Spring扩展知识) 5.1定义配置类:@Configuration 声明一个类为IOC容器 @Bean定义一个Bean 5.2.按照条件进行注入 5.3.@Impo ...

  2. Spring - SpringIOC容器详解

    一.什么是Spring IOC: Ioc—Inversion of Control,即“控制反转”,不是什么技术,而是一种设计思想. 在Java开发中,Ioc意味着将你设计好的对象交给容器控制,而不是 ...

  3. [Spring学习笔记 1 ] Spring 简介,初步知识--Ioc容器详解 基本原理。

    一.Spring Ioc容器详解(1) 20131105 1.一切都是Bean Bean可是一个字符串或者是数字,一般是一些业务组件. 粒度一般比较粗. 2.Bean的名称 xml配置文件中,id属性 ...

  4. Spring源码之九finishRefresh详解

    Spring源码之九finishRefresh详解 公众号搜索[程序员田同学],专职程序员兼业余写手,生活不止于写代码 Spring IoC 的核心内容要收尾了,本文将对最后一个方法 finishRe ...

  5. 【Spring】——声明式事务配置详解

    项目中用到了spring的事务: @Transactional(rollbackFor = Exception.class, transactionManager = "zebraTrans ...

  6. [js高手之路]深入浅出webpack教程系列2-配置文件webpack.config.js详解(上)

    [js高手之路]深入浅出webpack教程系列索引目录: [js高手之路]深入浅出webpack教程系列1-安装与基本打包用法和命令参数 [js高手之路]深入浅出webpack教程系列2-配置文件we ...

  7. 2017.2.13 开涛shiro教程-第十二章-与Spring集成(一)配置文件详解

    原博客地址:http://jinnianshilongnian.iteye.com/blog/2018398 根据下载的pdf学习. 第十二章-与Spring集成(一)配置文件详解 1.pom.xml ...

  8. Spring Boot源码中模块详解

    Spring Boot源码中模块详解 一.源码 spring boot2.1版本源码地址:https://github.com/spring-projects/spring-boot/tree/2.1 ...

  9. TCP三次握手与四次挥手详解

    目录 TCP三次握手与四次挥手详解 1.TCP报文格式 2.TCP三次握手 3.TCP四次挥手 4.为什么建立连接需要三次握手? 5.为什么断开连接需要四次挥手? 6.为什么TIME_WAIT状态还需 ...

随机推荐

  1. linux下close 掉socket 之后 阻塞的recv 不会立即返回

    转载自:http://www.cnblogs.com/wainiwann/p/3942203.html 在开发的一个基于rtmp聊天的程序时发现了一个很奇怪的现象. 在windows下当我们执行 cl ...

  2. linux,强大的history命令

    如果你经常使用 Linux 命令行,那么使用 history(历史)命令可以有效地提升你的效率.本文将通过实例的方式向你介绍 history 命令的 15 个用法. 使用 HISTTIMEFORMAT ...

  3. WINDBG解决cpu占高的问题

    https://blog.csdn.net/yenange/article/details/62886988 https://blog.csdn.net/zhushentian/article/det ...

  4. Gdb调试工具/ Makfile项目管理

    gdb调试工具 gcc -g main.c -o main 常用命令 命令            简写         作用 help                h            按模块列 ...

  5. Jmeter和LoadRunner的区别

    1.Jmeter的架构跟LoadRunner原理一样,都是通过中间代理,监控&收集并发客户端发现的指令,把他们生成脚本,再发送到应用服务器,再监控服务器反馈的结果的一个过程. 2.分布式中间代 ...

  6. July 29th 2017 Week 30th Saturday

    Where there is great love, there are always miracles. 哪里有真爱存在,哪里就有奇迹发生. Everyone expects there can b ...

  7. php非空验证

    我想说这种方法是不是很常用的非空验证,现在的普遍使用的是javascript来验证非空,但是作为学习php的一些知识点,还是可以看看的. 先来看看commit.php中的方法 <?php $db ...

  8. 关于 Can't connect to MySQL server on 'localhost' (10061) 的一个解决方案

    问题描述: 使用Navicat for mysql 无法远程连接到本地数据库,提示Can't connect to MySQL server on 'localhost' (10038) . 本地服务 ...

  9. Foj 2296 Alice and Bob(博弈、搜索)

    Foj 2296 Alice and Bob 题意 两个人博弈,规则如下:轮流取0~9中的数字,最后Alice所得的数字个数为1~n中,数位在Alice所取集合中出现奇数次的. 双方想获得尽量多,问A ...

  10. working-with-php-and-beanstalkd

    原文出处:http://www.lornajane.net/posts/2014/working-with-php-and-beanstalkd Working with PHP and Beanst ...