Отправка 4-байтового заголовка сообщения от клиента C# к Серверу Java

Довольно много ответов!

Я последовал этому примеру, который несколько человек тоже предложили: http://www.techrepublic.com/article/pro-tip-round-

Однако мне нужен был цветной круг, за прозрачным изображением. Для тех, кто заинтересован в том, чтобы сделать то же самое ...

1) Установите FrameLayout в ширину и высоту - в моем случае размер изображения (50dp). 2) Поместите ImageView, у которого есть src = "@drawable / ...", над ImageView, у которого есть изображение. Дайте ему идентификатор, в моем случае я назвал его iconShape 3) Drawable mask.xml должен иметь сплошной цвет #ffffffff 4) Если вы хотите динамически изменять цвет круга в коде, сделайте

ImageView iv2 = (ImageView) v.findViewById(R.id.iconShape);
Drawable shape = getResources().getDrawable(R.drawable.mask);
shape.setColorFilter(Color.BLUE, Mode.MULTIPLY);
iv2.setImageDrawable(shape);

7
задан aib 19 September 2008 в 14:27
поделиться

6 ответов

Это, как другие плакаты указали, вниз к порядку байтов.

Java DataInputStream ожидает, что данные будут обратным порядком байтов (сетевой порядок байтов). Судя по Моно документации (для эквивалентов как BinaryWriter), C# склоняется к тому, чтобы быть прямым порядком байтов (значение по умолчанию для Win32/x86).

Так, когда Вы пользуетесь библиотекой стандартного класса для изменения интервала на 32 бита '1' на байты, они приводят к различным результатам:

//byte hex values
Java: 00 00 00 01
  C#: 01 00 00 00

Можно изменить способ, которым Вы пишете ints в C#:

private static void WriteInt(Stream stream, int n) {
    for(int i=3; i>=0; i--)
    {
        int shift = i * 8; //bits to shift
        byte b = (byte) (n >> shift);
        stream.WriteByte(b);
    }
}

Править:

Более безопасный способ сделать это был бы:

private static void WriteToNetwork(System.IO.BinaryWriter stream, int n) {
    n = System.Net.IPAddress.HostToNetworkOrder(n);
    stream.Write(n);
}
11
ответ дан 6 December 2019 в 12:56
поделиться

Это просто, но Вы проверили порядок байтов? Это могло легко быть несоответствие между порядком байтов, Вы представили данные и порядок байтов, в котором Вы получаете.

2
ответ дан 6 December 2019 в 12:56
поделиться

Как все здесь уже указали, проблема, скорее всего, вызывается приложением C#, отправляющим ints в порядке с прямым порядком байтов, тогда как приложение Java ожидает их в сетевом порядке (обратный порядок байтов). Однако вместо того, чтобы явно перестроить байты в приложении C#, корректный путь состоит в том, чтобы полагаться на встроенные функции для преобразования от хоста до сетевого порядка (htons и подобные) - этот способ, которым Ваш код продолжит работать просто великолепно, даже когда работается машина с обратным порядком байтов.

В целом, при поиске и устранении неисправностей таких проблем, я нахожу полезным записать правильный трафик (например, Java к Java в случае) использование инструментов как netcat или wireshark, и затем сравнить его с неправильным трафиком для наблюдения, где это идет не так, как надо. Как дополнительное преимущество, можно также использовать netcat, чтобы ввести полученные/записанные заранее запросы в сервер или ввести полученные/записанные заранее ответы в клиент. Не говоря уже о том, что можно также изменить запросы/ответы в файле и протестировать результаты прежде, чем начаться с фиксацией кода.

2
ответ дан 6 December 2019 в 12:56
поделиться

Если бы Вы собираетесь быть обменом большим количеством данных, я рекомендовал бы реализовать (или найти) Потоковая обертка, которая может записать и считать ints в сетевом порядке. Но если действительно только необходимо записать, что длина делает что-то вроде этого:

using(Socket socket = ...){
  NetworkStream ns = new NetworkStream(socket);      
  ns.WriteByte((size>>24) & 0xFF);
  ns.WriteByte((size>>16) & 0xFF);
  ns.WriteByte((size>>8)  & 0xFF);
  ns.WriteByte( size      & 0xFF);
  // write the actual message
}
1
ответ дан 6 December 2019 в 12:56
поделиться

Я не знаю C#, но просто необходимо сделать эквивалент этого:

out.write((len >>> 24) & 0xFF);
out.write((len >>> 16) & 0xFF);
out.write((len >>>  8) & 0xFF);
out.write((len >>>  0) & 0xFF);
0
ответ дан 6 December 2019 в 12:56
поделиться

Sysetm. Сеть. Класс IPAddress имеет два статических вспомогательных метода: HostToNetworkOrder () и NetworkToHostOrder (), которые делают преобразование для Вас. Можно использовать его с BinaryWriter по потоку для записи собственного значения:

using (Socket socket = new Socket())
using (NetworkStream stream = new NetworkStream(socket))
using (BinaryWriter writer = new BinaryWriter(stream))
{
    int myValue = 42;
    writer.Write(IPAddress.HostToNetworkOrder(myValue));
}
0
ответ дан 6 December 2019 в 12:56
поделиться