Java.net服务器示例没有';行不通

Java.net服务器示例没有';行不通,java,sockets,Java,Sockets,我刚接触java.net,正在尝试制作一个简单的客户机-服务器应用程序。以下是服务器代码: public class Consumer extends Thread{ public Socket s; int num; public Consumer(int num, Socket s){ this.num = num; this.s = s; setDaemon(true); setPriority(

我刚接触java.net,正在尝试制作一个简单的客户机-服务器应用程序。以下是服务器代码:

public class Consumer extends Thread{

    public Socket s;
    int num;

    public Consumer(int num, Socket s){
        this.num = num;
        this.s = s;

        setDaemon(true);
        setPriority(NORM_PRIORITY);
        start();
    }

    public static void main(String args[]){
        try {
            int i = 0;

            ServerSocket server = new ServerSocket(3128, 0, InetAddress.getByName("localhost"));

            System.out.println("server started");
            while (true){
                new Consumer(i, server.accept());
                i++;
            }
        } catch (Exception e){

        }
    }

    public void run(){
        try {
            InputStream is = s.getInputStream();
            OutputStream os = s.getOutputStream();

            byte buf[] = new byte[64*1024];
            int r = is.read(buf);

            String data = new String(buf, 0, r);

            data = "" +num+": " +"\n" + data;

            os.write(data.getBytes());

            s.close();
        } catch (Exception e){
            System.out.println("init error: " + e);
        }
    }

}
当我启动它时-没有什么不好的事情发生,但当我从某个客户端发送smth时,我得到以下信息:

init error: java.lang.StringIndexOutOfBoundsException: String index out of range: -1
如何修复它?

可能是您的

int r = is.read(buf);
正在返回
-1
,因此此代码失败:

String data = new String(buf, 0, r);
检查流的结尾:

int bytesRead;
while( (bytesRead = in.read(buf)) != -1 ) {
 // then create a String from the byte[]
}
查看

返回:

读取到缓冲区的总字节数,如果由于到达流的结尾而没有更多数据,则为-1。

以及

抛出:

IndexOutOfBoundsException-如果偏移量和长度参数索引字符超出字节数组的边界


当您从输入流读取数据时,当
read
返回-1时,您就知道已经到达了流的末尾。看起来这里就是这样:r显示为-1,因为没有可读取的数据,然后程序继续尝试创建一个字符数为负数的字符串

应始终检查函数的返回值是否存在错误情况:

        int r = is.read(buf);

        if (r < 0) return; /* end of stream was reached */
我明白你的问题了。在你粘贴的示例中,你需要用命令行参数test1,test2,abc,mno运行程序SampleClient。尝试按链接中所述的方式运行,如下所示:

java SampleClient test1
java SampleClient test2
...
java SampleClient testN
实际上,您的程序没有运行,因为它没有读取数据,因为它没有参数

int r = is.read(buf);

返回-1,因此出现异常。

您的错误是启动程序时没有传递命令行参数

你应该从错误中吸取教训。在将来仔细研究系统的输入和输出

此外,您应该从异常中获得更多信息,因此堆栈跟踪是您的朋友


最后,IDE将对您有所帮助。例如,你可以下载NetBeans或Eclipse,它们将大大简化你作为开发人员的生活。

e.printStackTrace()给了你什么?我不知道你的情况。但是当我运行你的代码时,我的程序挂起在这行:新消费者(I,server.accept());可能是您的生产者类没有生成某些数据。如果生产者类存在,我建议在这个消费者类之前运行您的生产者类。您可以提供从哪里获得上述代码的链接吗?@rahulserver它是俄语,但您在这里:我按照下面的回答运行了代码,它是有效的。你能传递cmd行参数吗?当我在终端中运行它时,它给我以下信息:
a/dlp/main$java main.class test1线程“main”中的异常java.lang.NoClassDefFoundError:main/类由以下原因引起:java.lang.ClassNotFoundException:main.class at java.net.URLClassLoader$1.run(URLClassLoader.java:217)java.net.URLClassLoader.findClass(URLClassLoader.java:205)java.lang.ClassLoader.loadClass(ClassLoader.java:321)sun.misc.Launcher$AppClassLoader.loadClass(Launcher.java:294)java.lang.ClassLoader.loadClass(ClassLoader.java:266)的java.security.AccessController.doPrivileged(本机方法)找不到主类:main.class。程序将退出。
您的类名是什么?如果是SampleClient,首先使用javac SampleClient.java编译,然后使用java SampleClient。参考此链接了解更多说明:您是否也像java SampleClient test1一样将命令行参数传递给SampleClient?我按照描述做了所有事情,并使用相同的堆栈跟踪您运行代码的命令?您知道,我尝试先使用IDE启动它,但在几次boss快照后,我决定在控制台中尝试。在IDe中,我看到发送方发送消息,但接收方不发送消息。您的答案是最有用的
int r = is.read(buf);