黑马程序员技术交流社区

标题: 网络编程,TCP练习中的一点疑问,解答有奖 [打印本页]

作者: 付江涛    时间: 2014-7-30 23:14
标题: 网络编程,TCP练习中的一点疑问,解答有奖
本帖最后由 付江涛 于 2014-8-1 16:29 编辑

还是没怎么懂,继续往后看了,等复习的时候在想把~

客户端代码:
import java.io.*;
import java.net.*;
class TransClient
{
    public static void main(String[] args) throws Exception
    {
        Socket s=new Socket("192.168.1.103",10005);

        //定义读取键盘数据的流对象。
        BufferedReader bufr=new BufferedReader(new InputStreamReader(System.in));
        
        //定义目的,将数据写入到socket输出流。发给服务端。
        BufferedWriter bufOut=new BufferedWriter(new OutputStreamWriter(s.getOutputStream()));      -    1  - 问题处
        
        

        //定义一个socket读取流,读取服务端返回的大写信息
        BufferedReader bufIn=new BufferedReader(new InputStreamReader(s.getInputStream()));
        
        String line=null;

        while ((line=bufr.readLine())!=null)
        {
            if("over".equals(line))
                break;
            bufOut.write(line);
            bufOut.newLine();
            bufOut.flush();

            String str=bufIn.readLine();
            System.out.println("server:"+str);
            
        }

        bufr.close();
        s.close();

    }
}

         先抛开简写形式
上面问题处,代码一直理解不了。

毕老师说的是 目的 是 Socket输出流 ???
应该怎么理解?目的怎么会是流呢????

s.getInputStream() :返回的是OutputStream,难道流中能存数据?

实在是理解不了{:3_55:}

解答清楚者有重谢!


作者: 乐此不疲    时间: 2014-7-30 23:39
流中能存储数据啊,不然就不会有flush()动作了
你看下flush()的api:
     刷新该流的缓冲。如果该流已保存缓冲区中各种 write() 方法的所有字符,则立即将它们写入预期目标。然后,如果该目标是另一个字符或字节流,则将其刷新。因此,一次 flush() 调用将刷新 Writer 和 OutputStream 链中的所有缓冲区。
作者: 黄宝宝    时间: 2014-7-30 23:58
我是这样理解的,Socket 是两台机器间通信的端点,数据的流动需要用流来操作的,所以称为Socket  io流。。。。。。
作者: 长跑※终点    时间: 2014-7-31 00:16
目的为什么不能是流呢,流也能存放数据的。目的是指数据流向的地方,只是数据流向了socket输出流而已。
作者: 曲佳奇    时间: 2014-7-31 00:23
流中就是数据吧
TCP就相当于在客户端和服务端建立了桥梁 在服务端可以通过accept()方法获得一个Socket对象
客户端的OutputStream()对应 服务端InputStream()
客户端的InputStream()对应 服务端OutputStream()


作者: hmid    时间: 2014-7-31 00:24
“流”就相当于一根水管。一头进一头出。
BufferedWriter bufOut=new BufferedWriter(new OutputStreamWriter(s.getOutputStream()));      -    1  - 问题处
这里的s.getOutputStream()就是拿到那根管子,准备往里边倒水(写数据)。
作者: adent    时间: 2014-7-31 00:32
s.getInputStream() :返回的是IutputStream!!你代码也是这样写的。
作者: java—family    时间: 2014-7-31 01:32
本帖最后由 java—family 于 2014-7-31 01:35 编辑

tcp :客户端:              Socket s = new Socket("10.1.31.69",10002);          。。。。。。。。。。。。。。。             OutputStream out = s.getOutputStream();//获取了socket流中的输出流对象。           
      out.write("tcp演示,哥们又来了!".getBytes());
服务端:ServerSocket ss = new ServerSocket(10002);//
             建立服务端的socket服务         
       Socket s = ss.accept();//获取客户端对象           
    InputStream in = s.getInputStream();//读取客户端的数据,使用客户端对象的socket读取流        
        byte[] buf = new byte[1024];         
       int len = in.read(buf);           
     String text = new String(buf,0,len);
首先:流是可以存数据的:flush  就可以让流把数据输出去   上面代码端口(10002)相同,红色部分的流就是连着的,  数据可以从客服端到服务端。







作者: 青偆丶易逝〃    时间: 2014-7-31 09:12
socket有一个方法可以得到往服务器发送数据的输出流, 发送给服务器端,服务器处理了再发回来,你再创建个读取流读取, 很容易理解嘛。。 不知道楼主困惑哪里,
作者: 付江涛    时间: 2014-7-31 12:12
本帖最后由 付江涛 于 2014-7-31 14:17 编辑

当使用bufOut.write()时,底层还是使用了s.getOutputStream()获取的OutputStream对象的write()方法。 {:3_62:}

但以前学FileOutputStream FileInputStream的时候,
  1. FileOutputStream out=new FileOutputStream("1.txt");

  2.                 out.write("你好".getBytes());

  3.                 FileInputStream in=new FileInputStream("1.txt");

  4.                 byte[] buf=new byte[1024];

  5.                 int len=in.read(buf);

  6.                 System.out.println(new String(buf,0,len));
复制代码

new FileOutputStream和new FileInputStream必须传入参数,指定数据传入哪个文件。

就是不明白这,OutputStream为什么不需要传参数






作者: 付江涛    时间: 2014-7-31 12:15
乐此不疲 发表于 2014-7-30 23:39
流中能存储数据啊,不然就不会有flush()动作了
你看下flush()的api:
     刷新该流的缓冲。如果该流已 ...

那只是写入缓冲区了吧,看10楼
作者: java—family    时间: 2014-7-31 14:16
付江涛 发表于 2014-7-31 12:12
当使用bufOut.write()时,底层还是使用了s.getOutputStream()获取的OutputStream对象的write()方法。 {:3_6 ...

缓存流,只是装饰,他里面有了数组,但底层还是调用OutputStream对象的write()方法。
这和输入流的道理类似吧。最底层,还是只能一个一个写出去吧。你是怎么想的。。
作者: 付江涛    时间: 2014-7-31 14:18
java—family 发表于 2014-7-31 14:16
缓存流,只是装饰,他里面有了数组,但底层还是调用OutputStream对象的write()方法。
这和输入流的道理类 ...

这个我明白了,但又有个新的问题。10楼重新修改了一下。参数的问题
作者: icris    时间: 2014-7-31 14:25
付江涛 发表于 2014-7-31 12:12
当使用bufOut.write()时,底层还是使用了s.getOutputStream()获取的OutputStream对象的write()方法。 {:3_6 ...
  1. PrintStream out = System.out;
  2. out.println("hello");

  3. OutputStream out = System.out;
  4. out.write("hello".getBytes());
复制代码

看,也没有 new 对象,也没有传参数,也能正常运行不是。
所以回答是,因为它不需要传参数…
作者: java—family    时间: 2014-7-31 14:29
付江涛 发表于 2014-7-31 14:18
这个我明白了,但又有个新的问题。10楼重新修改了一下。参数的问题

Socket就是为网络服务提供的一种机制。
通信的两端都有Socket。
网络通信其实就是Socket间的通信。
数据在两个Socket间通过IO传输。
不知道这段换有用没。 以前在硬盘上,给个地址把数据存到哪里去。   现在他给了一个口子,让你把数据往里倒。
作者: 付江涛    时间: 2014-7-31 14:31
icris 发表于 2014-7-31 14:25
看,也没有 new 对象,也没有传参数,也能正常运行不是。
所以回答是,因为它不需要传参数… ...

PrintStream和OutputStream都指定了输出的位置:Sysetem.out

但我还是不明白s.getOutputStream()获取的OutputStream写数据时到底把数据写在哪?OutputStream并没有指定啊
作者: Moriarty    时间: 2014-7-31 14:36
我认为可以把Socket想象成一个飞机空中加油的管道,severSocket是为了确认那个飞机是否存在,而Socket是为了确定管道是否联通。其中getOutputSream就相当于那条管道,就是向服务器输出的那个流,现在你想把数据通过管道传入另一个飞机,那你就要将数据传入那个管道中,即那个流,所以你的目的是Stock输出流。
作者: 付江涛    时间: 2014-7-31 14:37
java—family 发表于 2014-7-31 14:29
Socket就是为网络服务提供的一种机制。
通信的两端都有Socket。
网络通信其实就是Socket间的通信。

意思就是说 Socket相当于硬盘、内存?客户端通过write()将数据写在服务端的Socket里,然后服务端通过reade()将Socket中的数据读取?再然后服务端通过write()将数据写去客户端的Socket中,客户端在通过自己的read()读取Socket中的数据,这样完成交互?是这样吗?Socket就相当于一个容器了?感觉太抽象{:3_55:}
作者: icris    时间: 2014-7-31 14:37
付江涛 发表于 2014-7-31 14:31
PrintStream和OutputStream都指定了输出的位置:Sysetem.out

但我还是不明白s.getOutputStream()获取的O ...

System.out 本身是一个 PrintStream ,它不是目标位置,但它有自己的目标位置(控制台或终端)。
s.getOutputStream() 本身是一个 OutputStream ,它也有自己的目标位置,就是流(或者说流的那一端的 InputStream)

你不要区别对待,如果一定要写出来才叫指定, System.out 也是没有指定的
作者: 付江涛    时间: 2014-7-31 14:39
icris 发表于 2014-7-31 14:37
System.out 本身是一个 PrintStream ,它不是目标位置,但它有自己的目标位置(控制台或终端)。
s.getOu ...

意思就是说 Socket相当于硬盘、内存?客户端通过write()将数据写在服务端的Socket里,然后服务端通过reade()将Socket中的数据读取?再然后服务端通过write()将数据写去客户端的Socket中,客户端在通过自己的read()读取Socket中的数据,这样完成交互?是这样吗?Socket就相当于一个容器了?
可不可以这么理解?
作者: icris    时间: 2014-7-31 14:47
付江涛 发表于 2014-7-31 14:39
意思就是说 Socket相当于硬盘、内存?客户端通过write()将数据写在服务端的Socket里,然后服务端通过read ...

理解怎么都行…知道这个 Output 是往外传的就行了…
IO 的最后一天有一个管道流,PipedInputStream 和 PipedOutputStream ,两个管道接起来传数据,差不多是一个道理
作者: baiiiu    时间: 2014-7-31 15:05
socket输出流,s.getOutputStream就是获取输出流,将键盘读入数据写入到该流中,也可以说传递到该流中,服务端还要再读的,也就是获取输入流




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