黑马程序员技术交流社区

标题: 请问下我这段代码中File对象创建文件失败的原因,后面有对... [打印本页]

作者: 杨玲    时间: 2013-2-16 17:29
标题: 请问下我这段代码中File对象创建文件失败的原因,后面有对...
本帖最后由 杨玲 于 2013-2-16 20:05 编辑
  1. static class MyServerThread implements Runnable
  2.         {
  3.                 //它有两个成员变量,一个是请求服务的客户端socket.另一个是用于统计上传文件数量的计数器.同时也
  4.                 //用于生成文件名
  5.                 private Socket socket;
  6.                 private long fileNumber;
  7.                
  8.                 private MyServerThread(Socket socket ,long fileNumber)
  9.                 {
  10.                         this.fileNumber =fileNumber;
  11.                         this.socket = socket;
  12.                 }

  13.                 @Override
  14.                 public void run()
  15.                 {        
  16.                         //得到客户端的IP地址.
  17.                         String id = socket.getInetAddress().getHostAddress();
  18.                         System.out.println(id+"...connected");
  19.                         //创建三个流对象,其中out,in,分别表示客户端的输入输出流,feedbackOut用于给客户端发送反馈信息,
  20.                         OutputStream out=null;
  21.                         InputStream in=null;
  22.                         OutputStream feedbackOut=null;
  23.                         try
  24.                         {
  25.                                 in = socket.getInputStream();
  26.                                 feedbackOut = socket.getOutputStream();        
  27.                         
  28.                                 int len;
  29.                                 byte[] b = new byte[1024];
  30.                                 //接收上传文件的类型信息.
  31.                                 len = in.read(b);
  32.                                 String fileType = new String(b,0,len);
  33.                                 //创建相应的文件并与out相关联.
  34.                                 File file = new File(System.getProperty("user.dir")+"\\file"+fileNumber+fileType);
  35.                                 file.createNewFile();        
  36.                                 out = new FileOutputStream(file);
  37.                                 //接收上上传的文件的内容信息.
  38.                                 while((len=in.read(b,0,b.length))!=-1)
  39.                                 {
  40.                                         out.write(b,0,len);
  41.                                 }
  42.                                 //发送反馈信息
  43.                                 feedbackOut.write("上传成功".getBytes());
  44.                                 
  45.                                 
  46.                         }
  47.                         catch(IOException e)
  48.                         {
  49.                                 e.printStackTrace();
  50.                                 
  51.                                 try {
  52.                                         feedbackOut.write("上传失败".getBytes());
  53.                                 } catch (IOException e1) {
  54.                                        
  55.                                         e1.printStackTrace();
  56.                                 }
  57.                         }
  58.                         finally//关闭流
  59.                         {
  60.                                 
  61.                                         try {
  62.                                                 if(out!=null)
  63.                                                         out.close();
  64.                                                 if(in!=null)
  65.                                                         in.close();
  66.                                                 if(feedbackOut!=null)
  67.                                                         feedbackOut.close();
  68.                                         } catch (IOException e) {
  69.                                                 // TODO Auto-generated catch block
  70.                                                 e.printStackTrace();
  71.                                         }
  72.                         }
  73.                 }
  74.                

  75.         }
  76.         
复制代码
下面是问题的描述:
        我这段代码是写的一个服务器的线程生成器,在服务器中当有客户端连接进来,就new 一个这个对象生成一个服务线程,可是在这里面有一个地方把我给搞晕了.
  1. //创建相应的文件并与out相关联.
  2. File file = new File(System.getProperty("user.dir")+"\\file"+fileNumber+fileType);
  3. file.createNewFile();        
复制代码
这一段代码报错,我另外开了一个文件,编译运行又是可以的,但是在这个程序里却是出现:
java.io.IOException: 文件名、目录名或卷标语法不正确。
        at java.io.WinNTFileSystem.createFileExclusively(Native Method)
        at java.io.File.createNewFile(Unknown Source)
        at com.itheima.Text9$MyServerThread.run(Text9.java:61)
        at java.lang.Thread.run(Unknown Source)
请教一下这个createNewFile方法,是什么情况?难道是因为多线程的原因?还望知道的大大们指点一下,谢谢了.
        
        


作者: 杨玲    时间: 2013-2-16 17:40
问题补充:我刚又试了下,连续运行客户端10次,竟然还TM的成功了一次....这玩意儿还有随机性?
作者: jonn    时间: 2013-2-16 18:56
加个逻辑判断,文件不存在情况下 ,再去创建一个与平台无关的文件
作者: jonn    时间: 2013-2-16 19:06
貌似 生成文件命名 fileNumber 变量要自增,fileType 返回是读取文件的字符串吧 这逻辑上太纠结了啊....{:soso_e136:}
作者: 杨玲    时间: 2013-2-16 19:14
赵文 发表于 2013-2-16 18:56
加个逻辑判断,文件不存在情况下 ,再去创建一个与平台无关的文件

呵呵,应该也有一部分这里的问题,我把这加了个逻辑:
  1.                                 if(file.exists())
  2.                                         file.createNewFile();       
  3.                                 out = new FileOutputStream(file);
复制代码
出现的情况是一次成功一次失败!
作者: 杨玲    时间: 2013-2-16 20:05
经过又是半小时的调试,我终于知道问题在哪了,NND,问题竟然出在多线程上.唉,蛋疼.搞定了,谢谢同志们了!
作者: 杨玲    时间: 2013-2-16 20:10
赵文 发表于 2013-2-16 19:06
貌似 生成文件命名 fileNumber 变量要自增,fileType 返回是读取文件的字符串吧 这逻辑上太纠结了啊....{:s ...

呵呵,file在服务器代码中自增嘛,然后传入给这个线程生成器,fileType是客户端上传上来的文件类型信息(比如.class , .java  , .txt这样的后缀名).当类型信息确定了以后才好创建相应类型的文件.这样实现的是可以上传什么文件这边就能拿到什么文件.不过问题我找到答案了,出在多线程上,难怪有时候可以有时候又不行呢,呵呵,还是谢谢你
作者: jonn    时间: 2013-2-16 20:22
杨玲 发表于 2013-2-16 20:10
呵呵,file在服务器代码中自增嘛,然后传入给这个线程生成器,fileType是客户端上传上来的文件类型信息(比如 ...

怎么解决了?给我瞧瞧....
作者: 杨玲    时间: 2013-2-16 21:50
赵文 发表于 2013-2-16 20:22
怎么解决了?给我瞧瞧....

这个代码没变,主要是客户端发送数据的时候的问题
  1. //客户端
  2.         static class MyClient
  3.         {
  4.                 public static void main(String[] args)
  5.                 {
  6.                        
  7.                         try
  8.                         {
  9.                                 //创建socket服务,并指定IP和端口号.
  10.                                 Socket socket = new Socket("127.0.0.1",10000);
  11.                                
  12.                                 //要上传 的文件对象.并与in输入流相关联.
  13.                                 File file = new File(System.getProperty("user.dir")+"//src//com//itheima//Text9.java");
  14.                                
  15.                                
  16.                                 FileInputStream in = new FileInputStream(file);
  17.                                 //得到文件的类型信息,并发送给服务器
  18.                                 String name = file.getName();
  19.                                 String fileType = name.substring(name.lastIndexOf('.'));                               
  20.                                 OutputStream out = socket.getOutputStream();
  21.                                 System.out.println(fileType);
  22.                                 out.write(fileType.getBytes());                               
  23.                                
  24.                                 int len ;
  25.                                 byte[] b =new byte[1024];
  26.                                 //先等待反馈信息,先前的客户端没有去接收反馈信息,而是直接就开始上传了.这样如
  27. //果这个线程接着运行就在服务端接收到的类型信息就会出错,所以加上这个信息就OK了
  28.                                 System.out.println(new String(b,0,socket.getInputStream().read(b)));
  29.                                 //开始上传文件.
  30.                                 while((len=in.read(b))!=-1)
  31.                                 {
  32.                                         out.write(b, 0, len);
  33.                                 }
  34.                                 //告诉服务器,文件上传完毕
  35.                                 socket.shutdownOutput();
  36.                                 //接收反馈信息
  37.                                 System.out.println(new String(b,0,socket.getInputStream().read(b)));
  38.                         }
  39.                         catch(IOException e)
  40.                         {
  41.                                 e.printStackTrace();
  42.                                 throw new RuntimeException("客户端错误!");
  43.                         }

  44.                 }
  45.         }
复制代码
主要就是加了一句等待反馈的语句就搞定了!
作者: 杨玲    时间: 2013-2-16 21:51
我调试了老半天才发现!晕咯!
作者: jonn    时间: 2013-2-16 23:31
杨玲 发表于 2013-2-16 21:51
我调试了老半天才发现!晕咯!

很好,这就是解决问题能力体现




欢迎光临 黑马程序员技术交流社区 (http://bbs.itheima.com/) 黑马程序员IT技术论坛 X3.2