【问题标题】:How to split the ByteArray by reading from the file in C++?如何通过从 C++ 中读取文件来拆分 ByteArray?
【发布时间】:2013-09-29 01:13:07
【问题描述】:

我编写了一个 Java 程序来将ByteArray 写入文件。而生成的ByteArray 是这三个 ByteArrays 的结果-

  • 2 个字节 是我的 schemaId,我使用短数据类型表示它。
  • 然后下一个 8 Bytes 是我的 Last Modified Date,我使用 long 数据类型表示它。
  • 剩余字节可以是可变大小,这是我的属性的实际值..

所以我现在有一个文件,其中第一行包含生成的 ByteArray,其中包含我上面提到的所有上述字节。现在我需要从 C++ 程序中读取该文件并读取包含 ByteArray 的第一行和然后按照我上面提到的那样相应地拆分生成的 ByteArray,以便我能够从中提取我的 schemaIdLast Modified Date 和我的实际属性值。

我所有的编码都是用 Java 完成的,而且我是 C++ 的新手……我可以用 C++ 编写一个程序来读取文件,但不确定我应该如何以这样的方式读取 ByteArray可以像我上面提到的那样拆分它..

下面是我的 C++ 程序,它正在读取文件并在控制台上打印出来..

int main () {
    string line;

    //the variable of type ifstream:
    ifstream myfile ("bytearrayfile");

    //check to see if the file is opened:
    if (myfile.is_open())
    {
        //while there are still lines in the
        //file, keep reading:
        while (! myfile.eof() )
        {
            //place the line from myfile into the
            //line variable:
            getline (myfile,line);

            //display the line we gathered:
            // and here split the byte array accordingly..
            cout << line << endl;
        }

        //close the stream:
        myfile.close();
    }

    else cout << "Unable to open file";

    return 0;
}

谁能帮我解决这个问题?谢谢。

更新

下面是我的 java 代码,它将生成的 ByteArray 写入一个文件,现在我需要从 c++ 中读回同一个文件..

public static void main(String[] args) throws Exception {

    String os = "whatever os is";
    byte[] avroBinaryValue = os.getBytes();

    long lastModifiedDate = 1379811105109L;
    short schemaId = 32767;

    ByteArrayOutputStream byteOsTest = new ByteArrayOutputStream();
    DataOutputStream outTest = new DataOutputStream(byteOsTest);
    outTest.writeShort(schemaId);
    outTest.writeLong(lastModifiedDate);
    outTest.writeInt(avroBinaryValue.length);
    outTest.write(avroBinaryValue);

    byte[] allWrittenBytesTest = byteOsTest.toByteArray();

    DataInputStream inTest = new DataInputStream(new ByteArrayInputStream(allWrittenBytesTest));

    short schemaIdTest = inTest.readShort();

    long lastModifiedDateTest = inTest.readLong();

    int sizeAvroTest = inTest.readInt();
    byte[] avroBinaryValue1 = new byte[sizeAvroTest];
    inTest.read(avroBinaryValue1, 0, sizeAvroTest);


    System.out.println(schemaIdTest);
    System.out.println(lastModifiedDateTest);
    System.out.println(new String(avroBinaryValue1));

    writeFile(allWrittenBytesTest);
}

    /**
 * Write the file in Java
 * @param byteArray
 */
public static void writeFile(byte[] byteArray) {

    try{
        File file = new File("bytearrayfile");

        FileOutputStream output = new FileOutputStream(file);
        IOUtils.write(byteArray, output);           
    } catch (Exception ex) {
        ex.printStackTrace();
    }
}

【问题讨论】:

  • 您的描述似乎表明您正在编写二进制数据,因此该 C++ 程序很可能不会打印任何内容(因为早期的 0 字节)或不会打印任何有用的内容.你看到了什么,你期望看到什么?
  • 作为提示,您需要了解二进制文本数据之间的区别以及如何读取/解析它们。
  • @yzt:是的..这个 C++ 程序不完整,因为我没有添加任何逻辑来拆分 ByteArray。或者它可能是另一种读取行中包含 ByteArray 的文件的方法。我是一名 Java 开发人员,所以对 C++ 不太熟悉......现在上面的 c++ 程序只会打印出每一行......
  • 从 Java 的角度来看,这没有意义。 1) Java 中没有标准的ByteArray 类型。 2) 如果您谈论的是byte[],那么您需要说明如何您是用Java 编写的。有很多方法可以实现不同的文件格式。
  • @StephenC:我用我的 Java 代码更新了我的问题,它将生成的 ByteArray 写入文件。如果有意义,请告诉我。

标签: java c++ c bytearray


【解决方案1】:

您似乎不想使用std::getline 来读取此数据。您的文件不是逐行写入文本数据 - 它基本上是二进制格式。

您可以使用std::ifstreamread 方法从输入流中读取任意数据块。您可能希望以二进制模式打开文件:

std::ifstream myfile("bytearrayfile", std::ios::binary);

从根本上说,您从文件中读取每条记录的方法是:

uint16_t schemaId;
uint64_t lastModifiedDate;
uint32_t binaryLength;

myfile.read(reinterpret_cast<char*>(&schemaId), sizeof(schemaId));
myfile.read(reinterpret_cast<char*>(&lastModifiedDate), sizeof(lastModifiedDate));
myfile.read(reinterpret_cast<char*>(&binaryLength), sizeof(binaryLength));

这将从文件中读取数据结构的三个静态成员。因为你的数据是可变大小的,你可能需要分配一个缓冲区来读取它,例如:

std::unique_ptr<char[]> binaryBuf(new char[binaryLength]);
myfile.read(binaryBuf.get(), binaryLength);

以上是示例,仅用于说明如何在 C++ 中处理此问题。您需要注意以下事项:

  • 以上示例中没有错误检查。您需要检查对ifstream::read 的调用是否成功并返回正确的数据量。
  • Endianness 可能是个问题,具体取决于数据来源和正在读取的平台。
  • 解释 lastModifiedDate 字段可能需要您编写一个函数来将其从 Java 使用的任何格式转换(我不知道 Java)。

【讨论】:

  • 非常感谢乔纳森。感谢您在这方面的帮助。您是否可以将这些代码与我的 c++ 示例放在一起?由于我是一名 Java 开发人员,至少需要几个小时才能弄清楚在哪里添加这些代码行......关于lastModifiedDate,我想按照它目前在 Java 中的方式来阅读,即 - 1379811105109..
猜你喜欢
  • 2021-07-27
  • 1970-01-01
  • 2020-12-18
  • 1970-01-01
  • 2022-06-27
  • 1970-01-01
  • 1970-01-01
  • 2022-08-18
  • 1970-01-01
相关资源
最近更新 更多