通过Java中的套接字发送字符串而不是字节
Posted
技术标签:
【中文标题】通过Java中的套接字发送字符串而不是字节【英文标题】:Send a string instead of byte through socket in Java 【发布时间】:2013-06-30 17:14:22 【问题描述】:如何使用 getOutputStream 方法发送字符串。它只能像他们提到的那样发送字节。到目前为止,我可以发送一个字节。但不是字符串值。
public void sendToPort() throws IOException
Socket socket = null;
try
socket = new Socket("ip address", 4014);
socket.getOutputStream().write(2); // have to insert the string
catch (UnknownHostException e)
System.err.print(e);
finally
socket.close();
提前致谢
【问题讨论】:
要发送一个字符串,您必须首先使用某种编码方案将其转换为字节。 UTF-8 是当今事实上的标准。 【参考方案1】:使用 PrintWriter 怎么样:
OutputStream outstream = socket .getOutputStream();
PrintWriter out = new PrintWriter(outstream);
String toSend = "String to send";
out.print(toSend );
编辑:找到我自己的答案并看到改进被讨论但被遗漏了。这是使用OutputStreamWriter 编写字符串的更好方法:
// Use encoding of your choice
Writer out = new BufferedWriter(new OutputStreamWriter(
new FileOutputStream(fileDir), "UTF8"));
// append and flush in logical chunks
out.append(toSend).append("\n");
out.append("appending more before flushing").append("\n");
out.flush();
【讨论】:
请注意,这里使用的是默认编码而不是显式编码,这很危险 PrintWriter 在 IMO 几乎总是一个坏主意。它吞噬异常的方式很可怕。 @JonSkeet 是的,我不太喜欢我自己提出的解决方案。让我们看看它是否适用于用户。正在考虑更好的解决方案。 @JunedAhsan:好吧,使用OutputStreamWriter
和write
就很简单,允许您指定编码,并避免异常讨厌。
@Ravindu 它会在“大部分时间”工作,具体取决于您通过网络发送的内容类型。所有字符串都必须使用特定的编码转换为字节。每个机器/jvm/os 中的“默认”编码可能不同。因此,您可以放心地假设,如果您不明确设置编码,总有一天会遇到问题。【参考方案2】:
使用OutputStreamWriter类来实现你想要的
public void sendToPort() throws IOException
Socket socket = null;
OutputStreamWriter osw;
String str = "Hello World";
try
socket = new Socket("ip address", 4014);
osw =new OutputStreamWriter(socket.getOutputStream(), "UTF-8");
osw.write(str, 0, str.length());
catch (IOException e)
System.err.print(e);
catch (UnknownHostException e)
System.err.print(e);
finally
socket.close();
【讨论】:
由于 *** 可怕的 6 字符编辑量策略,我不得不在这里评论一下,'UTF-8' 应该是“UTF-8”。请记住,单引号用于字符,而双引号用于字符串。【参考方案3】:两种选择:
将您的OutputStream
包装在OutputStreamWriter
中,这样您就可以发送字符串了
使用String.getBytes(encoding)
将字符串转换为字节
请注意,在这两种情况下,您都应该明确指定编码,例如“UTF-8” - 避免它只使用平台默认编码(这几乎总是一个坏主意)。
不过,这只会发送字符数据本身 - 如果您需要发送多个字符串,而另一端需要知道每个字符串的开始和结束位置,您将需要一个更复杂的协议。如果两端都是Java,你可以使用DataInputStream
和DataOutputStream
;否则您可能想提出自己的协议(假设它尚未修复)。
【讨论】:
嗯,....我对这个套接字及其输入/输出流有点困惑。接收部分呢?我的意思是我们如何区分数据传输是否只是一个字符串/文件? @JonSkeet @gumuruh:这听起来像是一个完全不同的问题。这个问题只是关于发送一个字符串 - 没有什么关于发送文件的。听起来您应该做更多的研究,然后如果您仍然感到困惑,请提出一个新问题。【参考方案4】:如果你有一个简单的字符串,你可以这样做
socket.getOutputStream().write("your string".getBytes("US-ASCII")); // or UTF-8 or any other applicable encoding...
【讨论】:
【参考方案5】:你可以像这样使用OutputStreamWriter
:
OutputStreamWriter out = new OutputStreamWriter(socket.getOutputStream());
out.write("SomeString", 0, "SomeString".length);
您可能要指定字符集,例如"UTF-8"
"UTF-16"
......
OutputStreamWriter out = new OutputStreamWriter(socket.getOutputStream(),
"UTF-8");
out.write("SomeString", 0, "SomeString".length);
或PrintStream
:
PrintStream out = new PrintStream(socket.getOutputStream());
out.println("SomeString");
或DataOutputStream
:
DataOutputStream out = new DataOutputStream(socket.getOutputStream());
out.writeBytes("SomeString");
out.writeChars("SomeString");
out.writeUTF("SomeString");
或者您可以在
中找到更多Writer
s 和OutputStream
s
java.io 包
【讨论】:
【参考方案6】:public void sendToPort() throws IOException
DataOutputStream dataOutputStream = null;
Socket socket = null;
try
socket = new Socket("ip address", 4014);
dataOutputStream = new DataOutputStream(socket.getOutputStream());
dataOutputStream.writeUTF("2"); // have to insert the string
catch (UnknownHostException e)
System.err.print(e);
finally
if(socket != null)
socket.close();
if(dataOutputStream != null)
dataOutputStream.close();
注意:您需要从接收端使用 DataInputStream readUTF() 方法。
注意:您必须在“finally”中检查 null;否则你稍后会遇到 NullPointerException。
【讨论】:
注意utf编码不是标准的,是修改后的。【参考方案7】:我在这篇文章中看到了很多非常有效的解决方案。我最喜欢的是使用 Apache Commons 来做写操作:
IOUtils.write(CharSequence, OutputStream, Charset)
基本上做例如:
IOUtils.write("Your String", socket.getOutputStream(), "UTF-8")
并捕获适当的异常。如果您正在尝试构建某种协议,您可以查看 Apache commons-net 库以获取一些提示。
你永远不会出错。 Apache commons-io 中还有许多其他有用的方法和类可以节省您的时间。
【讨论】:
【参考方案8】:旧帖子,但我可以在大多数帖子中看到相同的缺陷。在关闭套接字之前,刷新流。就像@Josnidhin 的回答一样:
public void sendToPort() throws IOException
Socket socket = null;
OutputStreamWriter osw;
String str = "Hello World";
try
socket = new Socket("ip address", 4014);
osw =new OutputStreamWriter(socket.getOutputStream(), 'UTF-8');
osw.write(str, 0, str.length());
osw.flush();
catch (IOException e)
System.err.print(e);
finally
socket.close();
【讨论】:
以上是关于通过Java中的套接字发送字符串而不是字节的主要内容,如果未能解决你的问题,请参考以下文章