爬坑记

一、HTML

跳转到的地方

1.1 checked属性值是true还是checked?

结论: 都可以,但是不推荐这两种方式,推荐仅设置checked属性不赋值

复选框标签具有checked属性,通过此属性可以设置复选框的选中状态。

非常简单的操作,但是还是有不少朋友存在后面类似的疑问,那就是不确定checked属性值是true还是checked。

因为两个属性值在实际代码中都有出现,并且都是有效的,也是导致出现疑问的主要原因。

下面通过代码实例详细进行一下分析,首先看一段代码实例:

<!DOCTYPE html>
<html>
    <head>
        <meta charset=" utf-8">
        <meta name="author" content="http://www.baidu.com/" />
        <title>百度</title>
        <style type="text/css">
            input{
                width:20px;
                height:20px;
            }
        </style>  
    </head>
    <body>
        <input type="checkbox" checked>
        <input type="checkbox" checked=true>
        <input type="checkbox" checked="checked">
    </body>
</html>

代码运行效果截图如下:

代码分析如下:

(1).仅设置checked属性不赋值,可以将复选框设置为选中状态。

(2).将checked属性值设置为true,也可以将复选框设置为选中状态。

(3).将checked属性值设置为"checked",也可以将复选框设置为选中状态。

上面三种情况都比较容易接受,因为在代码中比较常见,实际编码中仅推荐第一种方式,第二和第三种方式不被推荐.

具体参阅点击跳转

虽然后两种方式非常符合情理,能够将复选框设置为选中状态,也许这只是一个误会,这两个值并不是专属,有些属性值会让不少朋友匪夷所思,看如下代码实例:

<!DOCTYPE html>
<html>
    <head>
        <meta charset=" utf-8">
        <meta name="author" content="http://www.baidu.com/" />
        <title>百度/title>
        <style type="text/css">
            input{
                width:20px;
                height:20px;
            }
        </style>  
    </head>
    <body>
        <input type="checkbox" checked=false>
        <input type="checkbox" checked=true>
    </body>
</html>

代码运行效果截图如下:

是不是感觉很奇怪,按照常理,checked属性值为true是选中状态,那么属性值为false就是未选中状态。

然而事实是,即便属性值为false,复选框依然是选中状态。其实有这样有一个规律,那就是在HTML中,只要设置checked属性,无论是否赋值,或者赋何种值,复选框都是选中状态。但是在通过JavaScript进行操作的时候,并非如此。

看一段代码实例:

<!DOCTYPE html>
<html>
    <head>
        <meta charset=" utf-8">
        <meta name="author" content="http://www.baidu.com/" />
        <title>百度</title>
        <style type="text/css">
            input{
                width:20px;
                height:20px;
            }
        </style>  
        <script>
            window.onload=function(){
                let inputs=document.getElementsByTagName("input");
                inputs[1].checked=true;
                inputs[2].checked=false;
            }  
        </script>  
    </head>
    <body>
        <input type="checkbox">
        <input type="checkbox">
        <input type="checkbox" checked>
        <input type="checkbox" checked=false>
    </body>
</html>

代码运行效果截图如下:

代码分析如下:

(1).默认状态下,第二个复选框处于非选中状态,第三个处于选中状态。

(2).通过JavaScript动态两个复选框分别设置为选中和取消选中。

由此可见,在使用JavaScript进行动态操作的时候,设置checked属性值可为true或者false可以复选框设置为选中和非选中状态,经过测试,设置为"checked"也可以设置为选中状态,设置为undefined也可以取消选中,不过我们最好还是标准一些,毕竟MDN将checked属性阐述为布尔型类型,截图如下:

跳转到的地方

1.1.1 HTML 布尔属性值

有不少标签属性,无需设置属性值,比如disabled、checked与selected。

下面以复选框为例子做一下说明,看如下代码:

<!DOCTYPE html>
<html>
    <head>
        <meta charset=" utf-8">
        <meta name="author" content="http://www.baidu.com/" />
        <title>百度</title>
        <style type="text/css">
            input{
                width:20px;
                height:20px;
            }
        </style>  
    </head>
    <body>
        <input type="checkbox" checked>
        <input type="checkbox" checked=true>
        <input type="checkbox" checked="checked">
    </body>
</html>

代码运行效果截图如下:

checked属性不需要设置值,只需要添加此属性,复选框就会被选中。

disabled或者selected等属性也是同样的道理,无需设置属性值,可以节省若干代码量,也符合标准。

上述几个属性还有一些地方需要注意,具体参阅点击跳转

1.2 路径问题

1.2.1 绝对路径和相对路径及根路径

先给出一个网站结构图做实例加深理解:
A网站(域名为http://www.a.com):/include/a-test.html,/img/a-next.jpg;
B网站(域名为http://www.b.com):/include/b-test.html,/img/b-next.jpg

相对路径是从引用的网页文件本身开始构建的,如果在A网站中的a-test.html中要插入图片a-next.jpg,可以这样做:< img src="../img/a-next.jpg" />重点是img前面的…/,表示从html处于的include开始起步,输入一个…/表示回到上面一级父文件夹下,然后再接着img/表示又从父级文件夹下的img文件开始了,最后定位img下面的a-next.jpg。

绝对路径 如果是Web项目一般带有网站的域名,例如: 如果在A网站中的a-test.html中要插入图片a-next.jpg,需要这样这样写:< img src="http://www.a.com/img/a-next.jpg" >,将图片路径上带有了域名信息,再打个比方:如果在A网站中的a-test.html中要插入B网站的图片b-next.jpg,就需要这样写:< img src="http://www.b.com/img/b-next.jpg" >,这种方法适用与在不同网站之间插入外部网站的图片。
如果是在本地电脑上绝对路径应该像这样: F:\pan\Javawebcode\code\goods\WebRoot\jsps\css\user\regist.css,从文件所在的磁盘符开始到该文件名

根路径是从网站的最底层开始起,一般的网站的根目录就是域名下对应的文件夹,就如D盘是一个网站,双击D盘进入到D盘看到的就是网站的根目录,这种路径的链接样式是这样的:如果在A网站中的a-test.html中要插入图片a-next.jpg,可以这样做:< img src="/img/a-next.jpg" >以/开头表示从网站根目录算起,找到根目录下面的img文件夹下的next.jpg。

**简言之: **

  • 相对路径: ../ 或者 ../../ 或者像这种 temp/test/test.html
  • 绝对路径: 盘符开始 或 http 开始
  • 根路径: 一般以/开头
1.2.2 转发和重定向中的/

①: 转发时"/“代表当前项目的根路径 ;重定向时”/"代表当前服务器的根路径

比如:

转发:/代表http://localhost:8080/工程名/ 举例: request.getRequestDispatcher("/jsp/system/index.jsp").forward(request,response);

重定向:/代表http://localhost:8080/

另外:

超链接中href的/代表http://localhost:8080/

标签的Src 属性的值中/代表http://localhost:8080/

c标签/代表http://localhost:8080/工程名/

include指令中file的/代表http://localhost:8080/工程名/<%@ include file = "/jsps/header.jsp" %>

1.2.3 Javaweb工程中在写路径时,为什么不包含WebContent(eclipse中默认名)

JavaWeb项目中引用的路径其实是编译后的路径: 即下图 右边部分的路径:

例如: target.jsp的绝对路径为: http://localhost:8080/Chicken/good/target.jsp

1.3 中文乱码问题

1)设置页面编码,

若是jsp页面: 则<%@page language="java" pageEncoding="UTF-8" contentType="text/html;charset=UTF-8" %>

若是html页面,在网页头部(< head>< /head>)中添加下面这段代码:

< meta http-equiv="Content-Type" content="text/html; charset=utf-8" />

2)将form表单提交方式变为post方式,即添加method=“post”;)在Servlet类中编写代码request.setCharacterEncoding("UTF-8")而且必须写在第一行。

3)如果是get请求,在Servlet类中编写代码

byte [] bytes = str.getBytes("iso-8859-1");

String cstr = new String(bytes,"utf-8");

  1. 或者直接修改Tomcat服务器配置文件server.xml增加内容:

URIEncoding="utf-8"

二、Java

2.1 集合中List 和 Set 区别,以及 定制排序和选择排序

2.1.1 区别:

List接口: 存储有序,可重复

Set接口:存储无序,不可重复

2.1.2 值得注意的地方:

注:

①: 存储有序/无序: 指的是元素在底层存放的位置有序/无序.

而不是根据遍历出来的顺序与存入的顺序是否一致来说明有序/无序.

②: 不可重复性:当向Set中添加相同的元素的时候,后面的这个不能添加进去

另外Map中与这相似: 判断两个key是否相同,若相同,则只能添加进后添加的那个元素

③: 一个TreeSet对象必须存储同一种数据类型,不能既存储Integer 又存储String类型, 而HashSet和LinkedHashSet则可以存储不同类型.

④: HashSet 遍历出来的顺序与存入时的顺序不同.但LinkedHashSet是相同的

⑤: 向TreeSet中添加的元素时,首先按照compareTo()进行比较,一旦返回0,虽然仅是两个对象的此属性组相同,但是程序会认为这两个对象相同而不管其他属性是否相同,进而后一个对象不能添加进来

⑥: 使用TreeSet时, compareTo()与hashCode()以及equals()三者保持一致!

⑦: 关于HashTable 古老的实现类,线程安全,不建议使用; Properties:Hashtable的子类,常用来处理属性文件。键和值都为String类型的

Vector(古老的实现类,线程安全的,但效率低于ArrayList)

⑧: 如果存入集合中的元素是自定义类的对象。要求:自定义类要重写equals()方法。

2.1.3 选择排序和定制排序

当向TreeSet中添加自定义类的对象时,涉及到两种排序方法:①自然排序②定制排序

①自然排序:(实现comparable接口,并重写compareTo方法)(从小到大,从大到小排序)

②定制排序:(实现Comparator接口,重写compare方法)—>也就是按照指定的属性排序(例如: 自定义了一个Person类含有name属性和age属性,我想指定按照age属性的值且从大到小排序)

两者区别:

自然排序要求在自定义类中实现java.lang.Comparable接口并重写其compareTo(Objecto)方法

//当向TreeSet中添加Person类的对象时,依据此方法,确定按照哪个属性排列
public class Person implements Comparable<Person> {
    private String name;
	private Integer age;
    //private int age;

    
    @Override
    public int compareTo(Object o) {
        if (o instanceof Person) {
            Person p = (Person) o;
            //		return this.name.compareTo(p.name);//因为name是String类型,String类重写了compareTo方法,所以按照姓名从小到大排序
            //		return this.age.compareTo(p.age);//因为age是包装类Integer类型,Integer类重写了compareTo方法,所以按照年龄从小到大排序
            //		return this.age - p.age;   //如果age为基本数据类型int型,int不是类,所以没有compareTo方法,所以只能用减号-


            //如果想按照年龄从大到小排序,只需在前面加一个负号即可
            //		return -(this.age.compareTo(p.age));//按照年龄从大到小排序
            //		return -(this.age - p.age);//按照年龄从大到小排序
            

            int i = this.age.compareTo(p.age);
            if (i == 0) {//年龄相同
                return this.name.compareTo(p.name);//接着比较姓名,按照姓名的首字母根据字典顺序排序
            } else {//年龄不相同
                return i;//按照年龄排序
            }		
        }
        return 0;
    }
}

选择排序可以在方法中创建一个实现了Comparator接口的类对象(匿名内部类),并重写compare方法.

@Test
public void testTreeSet2() {
    // 1.创建一个实现了Comparator接口的类对象
    Comparator com = new Comparator() {


        //向TreeSet中添加Customer类的对象,在此compare()方法中,指明是按照Customer的哪个属性排序的
        @Override
        public int compare(Object o1, Object o2) {
            // TODO 自动生成的方法存根
            if(o1 instanceof Customer && o2 instanceof Customer) {
                Customer c1 = (Customer) o1;
                Customer c2 = (Customer) o2;
                //	return c1.getId().compareTo(c2.getId());
                int i = c1.getId().compareTo(c2.getId());

                //这种方式,返回结果为[name=CC, id=1001], [name=DD, id=1001], [name=BB, id=1002], [name=AA, id=1003], [name=GG, id=1004]
                if (i == 0) {     //如果id相同
                    return c1.getName().compareTo(c2.getName());//接着比较姓名
                }

                //id不同
                return i; //即return c1.getId().compareTo(c2.getId())且值为-1或者1
            }


            /*	
				// 这种方式,返回结果为 [name=DD, id=1001], [name=BB, id=1002], [name=AA, id=1003], [name=GG, id=1004]
				if(c1.getId()!=c2.getId()) {
					return i; //即return c1.getId().compareTo(c2.getId())且值为-1或者1
				} else {

					return c1.getName().compareTo(c2.getName());
				}

			}
	*/
            //o1或o2不是Customer类的对象
            return 0;
        }
    };

    //2. 将此对象作为形参传递给TreeSet的构造器
    TreeSet set = new TreeSet(com);
    //3. 向TreeSet中添加Comparator接口中的compare方法中涉及的类的对象。
    set.add(new Customer("AA",1003));
    set.add(new Customer("BB",1002));
    set.add(new Customer("GG",1004));
    set.add(new Customer("DD",1001));
    set.add(new Customer("CC",1001));

    for (Object str:set) {
        System.out.println(str);
    }

}

或者:

class Test02 {
    public static void main(String[] args) {
        List<Student> list = new ArrayList<>(); // Java 7的钻石语法(构造器后面的尖括号中不需要写类型)
        list.add(new Student("Hao LUO", 33));
        list.add(new Student("XJ WANG", 32));
        list.add(new Student("Bruce LEE", 60));
        list.add(new Student("Bob YANG", 22));

        // 通过sort方法的第二个参数传入一个Comparator接口对象
        // 相当于是传入一个比较对象大小的算法到sort方法中
        // 由于Java中没有函数指针、仿函数、委托这样的概念
        // 因此要将一个算法传入一个方法中唯一的选择就是通过接口回调
        Collections.sort(list, new Comparator<Student> () {
            @Override
            public int compare(Student o1, Student o2) {
                return o1.getName().compareTo(o2.getName());    // 比较学生姓名
            }
        });

        for(Student stu : list) {
            System.out.println(stu);
        }
        //      输出结果:
        //      Student [name=Bob YANG, age=22]
        //      Student [name=Bruce LEE, age=60]
        //      Student [name=Hao LUO, age=33]
        //      Student [name=XJ WANG, age=32]
    }
}

2.1.4 集合的遍历有四种方式 :

①使用Iterator迭代器

②增强型for循环

③普通for循环

④Iterator迭代器的"古老版本"Enumeration 接口

Public static void main(String[]args){
    Enumeration enu=new StringTokenizer("ab-c*-df-g","-");
    while(enu.hasMoreElements()){
        System.out.println(enu.nextElement());
    }
}
//结果: 
ab
c*
df
g

三、JSP

3.1 JSP中括号匹配问题

注意:if语句的最后一个括号必须和else被分在同一个java脚本元素中

<%
	if(session.getAttribute("type3").equals("manager")) {
%>
<%
	Date creatTime = new Date(session.getCreationTime());
	Date lastAccessedTime = new Date(session.getLastAccessedTime());  
	session.removeAttribute("name3");
	out.println("删除名字为name3的属性后,");
	out.println("再获取名为name3的属性:");
	out.println(session.getAttribute("name3")+"<br>"); 
%>


<%
}       //这里出过错误;注意:if语句的最后一个括号必须和else被分在同一个java脚本元素中
else
{
   %>
<a href="user.jsp">进入使用界面</a>
<%
}
%>

3.2 空格问题:

报错: The JSP specification requires that an attribute name is preceded by whitespace

意思是:JSP规范要求在一个属性的名字之前应该是空格。

3.3 注释问题

①: JSP动作标志后面不能有注释

<jsp:forward page="/False.jsp">                //10 行
改为:
<jsp:forward page="/False.jsp">    

②: 当标签没有配对参数时,配对标签不能换行

jsp异常: Expecting "jsp:param" standard action with "name" and "value" attributes错误

解决方法如下:

<body>
<jsp:include page="include/header.jsp">
</jsp:include>
</body>

改为:
<body>
<jsp:include page="include/header.jsp"></jsp:include><!-- 此处必须在同一行,不能换行 -->
</body>

3.4 双引号问题

.jsp文件在tomcat运行,报错提示Attribute value request.getParameter("name") is quoted with "which must be escap

例如:
<jsp:include page="action.jsp" flush="true">   
<jsp:param name="a1" value="<%=request.getParameter("name") %>" />    
<jsp:param name="a2" value="<%=request.getParameter("password") %>"/>
</jsp:include>  
会导致报错

改为:
<jsp:include page="action.jsp" flush="true">   
<jsp:param name="a1" value="<%=request.getParameter(\"name\") %>" />    
<jsp:param name="a2" value="<%=request.getParameter(\"password\") %>"/>
</jsp:include>  
即可解决

未完待续…

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

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值