Java改错学习法

2018-03-26作者:朱福喜著编辑:Solomon

常言道,万事开头难,学 Java 更是如此。编程还有与许多事情不一样的地方,例如, 说话时遗漏个字,一般人也听得懂,写文章时输入个错别字,别人可能也能看懂,但编程 不一样,它不能出现半点差错,否则会毫不留情,不让你通过,因此使得很多人,甚至是 聪明人都产生了畏难心理。如何让初学者克服这个障碍呢?这就是本书的出发点。


编程的人不需要太聪明,但需要培养机械和逻辑思维的能力。有时候,过于聪明反而 会给自己造成更多的编程困难。本书正是基于这一点,虚构了一个场景,刻画了两个不同 的形象。
一休:日本动画片《聪明的一休》中的主人公,聪明,肯动脑筋,遇到困难的问题就 冥思苦想,是很有灵气、顽皮的小精灵的象征。愚公:中国寓言中倔强的老头,为搬去挡在家门的大山,挖山不止,是有勇气、肯实 干的象征。在本书虚构的学习环境中,一休是想学习 Java 的小生;愚公是埋头编程的 Java 教头。 愚公教一休如何改错学 Java,这便是本书的主题。本书就围绕他们的对话而展开。参与本书编写的人员,除封面署名作者外,还有朱三元、刘世超、朱丽达、陈端直、 王瑛、周孟、束元等,在此编者对他们表示衷心的感谢。


   愚公:

Java 作为一门编程语言,最好的学习方法就是动手编写代码。当学习一个概念 后,就可以自己编写一个简单的程序来运行一下,看看有什么结果,然后再多调用几个类 的方法,比较一下运行结果,这样就能够非常直观地学会 Java 了,而且记忆深刻。
学会以后,不能仅仅满足于把代码调通,你应该想想如果我不这样编写,换个方式行 不行。记住,学习编程就是一个破坏的过程,把书中的范例、自己学习的程序在运行通过 以后,不断尝试利用不同的方法实现,不断尝试破坏代码的结构,看看会有什么结果。通 过这样的方式,你就能很彻底地掌握 Java。


  一休:

是啊,我也想这么做。但一动手就会碰到问题,我想啊想,就是想不出为什么。 愚公:Java 语言和人类语言在某些方面是类似的,只是它是讲给计算机听的,在许多
方面都存在一些特殊约定,要通过计算机的运行去体会它,而不是靠你有多聪明去想象它。


javaee.jpg



一、动手才是硬道理


人人都夸我聪明,好像没有什么能够难倒我的问题。可是,碰到 Java 编程这玩 意,我就不灵了,动手就错,我想破了脑壳就是想不出用什么招数治它,气得我摔坏机器 也无济于事。哈哈,我知道其中的缘由。编程这活不是光靠聪明就能搞定的。不靠聪明靠什么? 靠的是一股傻劲,就像我一样,每天挖山不止。我学的是“假挖”(Java),难道要真的挖吗? 我指的是要多动手,动手才是硬道理。您能具体讲解一下吗?


Java 作为一门编程语言,最好的学习方法就是动手编写代码。当学习一个概念 后,就可以自己编写一个简单的程序来运行一下,看看有什么结果,然后再多调用几个类 的方法,比较一下运行结果,这样就能够非常直观地学会 Java 了,而且记忆深刻。学会以后,不能仅仅满足于把代码调通,你应该想想如果我不这样编写,换个方式行 不行。记住,学习编程就是一个破坏的过程,把书中的范例、自己学习的程序在运行通过 以后,不断尝试利用不同的方法实现,不断尝试破坏代码的结构,看看会有什么结果。通过这样的方式,你就能很彻底地掌握 Java。是啊,我也想这么做。但一动手就会碰到问题,我想啊想,就是想不出为什么。Java 语言和人类语言在某些方面是类似的,只是它是讲给计算机听的,在许多方面都存在一些特殊约定,要通过计算机的运行去体会它,而不是靠你有多聪明去想象它。


二、从简单的程序开始


在学习过程中,我点子虽多,但总觉得 Java 太难。万事开头难,我们可以从简单的程序开始。举个例子,我们都编过 HelloWorld 吧?是的,我会编,我编给你看。

     public class HelloWorld

       {

           public static void Main(String[] args) 

          { System.out.println("Hello World"); }

     }

你看看,一动手就错了! 一休:哪有错?编译都通过了。你执行看一下。错在哪里,你知道吗?应该是没有 main 方法,但是我编了 Main 方法,编译也没有指出错误啊?你编了一个 Main 方法,这在语法上没有错,但是没有 Java 虚拟机要的 main 方 法,main 方法是入口,没有它,就像建造一栋房子没有预留门的位置一样,没有地方可以 进入。那 main 方法前面还带了很多头衔,可以不这样写吗?不行,一定要写 public static void main。很多初学者都不理解为什么 main 方法一定要这样来定义:public static void main(String[] args)是否可以修改一下呢?


很简单,把 main 换个名字运行一下,看看报什么错误,然后根 据出错信息进行分析;把 main 之前的 public 去掉再试试看;把 static 去掉,看看还能不能 运行;是否一定要是 String[]数组呢?把 String[]改成 int[]或者 String 试试看;想知道参数名 称是否必须写为 args 吗?可以把 args 改成其他名字,看看运行结果如何。我把 HelloWorld 程序反复改了七八次,不断运行,分析运行结果,终于明白原 因了——Java 虚拟机就是这样约定的,难道一点也不能改动吗?也不是,public 可以与 static 交换一下位置;String[] args 可以写成 String args[];args 也可以写成其他名字。终于会写 main 方法了。体会到了吗?所以,动手才是硬道理呀!


三、如何设置路径


我是想学您挖山不止的精神,可是总是使不上劲啊!为什么?每次编译和运行程序,不是找不到这个文件就是找不到那个文件,有时候把我 气得想砸机器。你应该了解关于寻找 class 文件的原理,建议开始学习 Java 的 时候在命令行窗口编译和运行 Java 程序,不要借助 JCreator 或者 Eclipse 等 IDE 去做那些 事情。首先要正确设置 classpath 环境变量,它就是一个路标,指出你要找的类文件可能存 放在哪些路径之下。我也对照书中讲的方法设置了 classpath,但有时候就是找不到。


运行时的状态不好掌握,可能是你设置后没有重新启动计算机,也可能是运行 其他程序时改变了环境,但我有个“笨”办法:编译程序时使用:javac -classpath yourpath *.java。执行程序时使用:java -classpath yourpath *.class。“-classpath”的作用是指定查找用户类文件和注释处理程序的位置,所以它后面要跟 一个路径,也就是你的源程序文件或类文件所放的位置。有时候又显示找不到命令文件 java 和 javac 在哪里。那你应该先设置好 path 变量,使系统可以找到 jdk 的 bin 目录。我也有一个“笨”办法,即把编译或执行命令文件的绝对路径指出来。>d:jdk16injavac -classpath yourpath *.java 再“笨”一点的办法就是把要编译的源程序的位置。>d:jdk16injavac -classpath d:myprogHello.java 这个“笨”办法一定可行。你还可以利用下面的方法指定存放生成类文件的位置: javac -d <目录> *.java


以上这些都是没有办法时的办法。是的,当然,你还是应该从原理上弄清楚为什么要设置这些环境变量。首先, 了解过计算机的基础知识后就会知道,设置 path 环境变量是为了使系统能够找到要执行的 命令;而设置 classpath 的目的是告诉 Java 虚拟机去哪里寻找你的 class 文件。JVM 要依靠 AppClassLoader 加载类文件。可以在前面编写的 HelloWorld 类中加入如下语句:

System.out.println(new HelloWorld().getClass().getClassLoader().toString()); 这样就可以简单测试出 HelloWorld 的加载类为 sun.misc.Launcher$AppClassLoader。 我马上去试试。这就对了,一定要多动手,万事开头难!


四、正确引用对象


我又碰到问题了,还是那个 main。我把字符串"Hello World"搬到 main 之 外就不行了,代码好像没有什么问题:

               class StaticError

                { 

                    String mystring="Hello World";

                       public static void main(String args[])

                    { System.out.println(mystring);

                   } 

                 }

但编译时错误信息为:

nonstatic variable mystring cannot be referenced from a static context


犯错误不要紧,只要每次不犯同样的错误就行了,正所谓“失败是成功之母”, 如果把所有的错误都犯尽了,编写的程序也就不会再出错了。您的意思是让我使劲犯错误吗? 愚公:那也要看是什么样的错误。犯一个错误,纠正之后要弄懂一个概念。就你这个错误而言,还是过程式编程的思维:所有的过程可以访问所有的全局变量。在 Java 中,过程和函数统称为方法,方法分为类方法和实例方法,变量也分为类变量 和实例变量。所谓类变量和类方法都是对整个类而言的,类方法只能访问类变量,换句话 说,类方法不能访问实例变量。实例方法可以访问实例变量和类变量。该程序中,main 方 法是静态的,只能访问静态变量。但还是觉得抽象。


比方说,“人民”是一个类,“制定宪法”是一个类方法,“人大常委会”是 一个类变量,张三、李四、王麻子是“人民”这个类的实例变量,“制定宪法”可以使用 “人大常委会”这个类变量,但“制定宪法”就不能专门针对张三、李四、王麻子。这有 点类似于“为人民服务”,而不是针对某个人服务。怪不得总听别人说“我是为人民服务的,不是为你一个人服务的”,那么这个 问题怎么解决呢?解决的办法有两种,第一种方法是将变量 mystring 改成类变量。 我来改,就在声明mystring 字符串的前面加上 static 即可,程序写好了。

         class StaticError

          {

             static String mystring="hello";

             public static void main(String args[]) 

               { 

            System.out.println(mystring);

                } 

            }

改得不错。第二种方法是先先创建一个类的实例,然后通过该对象访问该变量。 一休:这个方法我需要想一想。 愚公:再具体一点就是先创建当前类的一个对象,然后通过该对象访问 mystring 变量。代码编写出来了。

             class NoStaticError

             { 

                String mystring="hello";

                 public static void main(String args[])

                    { 

                        NoStaticError noError;

                        noError=new NoStaticError(); System.out.println(noError.mystring);

                     }

                 }

愚公:这就对了。有时候碰到一个错误你应该高兴,高兴的是又有一个机会学到新的 知识了。


关注微信公众号书问, 免费领取万本好书




内容来源:书问

作者朱福喜
出版清华大学出版社
定价39元
书籍比价

分享到

扫描二维码 ×

参与讨论

电子纸书

Java改错学习法

朱福喜
清华大学出版社[2013] ¥20

Java入门1·2·3——一个老鸟的Java学习心得

臧萌
清华大学出版社[2010] ¥28

Java编程手记——从实践中学习Java

欧二强 等
清华大学出版社[2013] ¥40

Java程序设计完全学习手册

王作启、伍正云
清华大学出版社[2014] ¥47

Java Web实战开发完全学习手册

杨光、伍正云
清华大学出版社[2014] ¥35

成人学习者境外学习意愿、偏好与决策----两岸四地比较研究

梁文慧、王政彥
清华大学出版社[2015] ¥40

机器学习:从公理到算法

于剑
清华大学出版社[2017] ¥48

类别不平衡学习:理论与算法

于化龙
清华大学出版社[2017] ¥35

基于机器学习的遥感影像分类方法研究

刘颖
清华大学出版社[2014] ¥29

出版业领先的TMT平台

使用社交账号直接登陆

Copyright © 2018 BookAsk 书问   |   京ICP证160134号


注册书问

一键登录

Copyright © 2018 BookAsk 书问   |   京ICP证160134号