如何使用 unique_ptr 创建 blob 流?
How to create blob stream using unique_ptr?
当使用以下代码时,我成功地将图像保存到“图像”blob 字段中:
if (OpenDialog1->Execute()) {
ADOTable1->Insert();
TStream* BlobStream = ADOTable1->CreateBlobStream(ADOTable1->FieldByName("Image"), bmWrite);
std::unique_ptr<TFileStream> FileStream(new TFileStream(OpenDialog1->FileName, fmOpenRead));
BlobStream->CopyFrom(FileStream.get(), FileStream->Size);
delete BlobStream;
ADOTable1->Post();
}
但是,我也希望使用 std:unique_ptr
创建 BlobStream
对象,这样我就可以避免手动 delete
。当我尝试
if (OpenDialog1->Execute()) {
ADOTable1->Insert();
std::unique_ptr<TStream> BlobStream(ADOTable1->CreateBlobStream(ADOTable1->FieldByName("Image"), bmWrite));
std::unique_ptr<TFileStream> FileStream(new TFileStream(OpenDialog1->FileName, fmOpenRead));
BlobStream->CopyFrom(FileStream.get(), FileStream->Size);
ADOTable1->Post();
}
我收到 无法插入空行 错误。我在这里做错了什么?我正在使用 C++ Builder 10.3.3。
在原始代码中,您在调用 Post()
.[=33= 之前 delete
正在 调用 blob TStream
对象 ]
根据 TADOBlobStream
文档:
http://docwiki.embarcadero.com/Libraries/en/Data.Win.ADODB.TADOBlobStream.Destroy
Destroy [ie, the destructor] performs the following tasks:
Sets the field's data.
Changes the field object's Modified property to true.
Triggers a field change event in the field's dataset object.
Calls the inherited destructor.
因此,您在 Post()
之前设置了 blob 的字段数据,一切都很好。
在更新的代码中,当 BlobStream
超出范围 在 调用 Post()
。因此,尚未设置字段数据,因此出现错误。
为了确保 blob TStream
对象在调用 Post()
之前被销毁,您可以:
- 在
BlobStream
周围放置一个新范围:
if (OpenDialog1->Execute()) {
std::unique_ptr<TFileStream> FileStream(new TFileStream(OpenDialog1->FileName, fmOpenRead));
ADOTable1->Insert();
{
std::unique_ptr<TStream> BlobStream(ADOTable1->CreateBlobStream(ADOTable1->FieldByName("Image"), bmWrite));
BlobStream->CopyFrom(FileStream.get(), FileStream->Size);
}
ADOTable1->Post();
}
- 在
BlobStream
上手动调用 reset()
:
if (OpenDialog1->Execute()) {
std::unique_ptr<TFileStream> FileStream(new TFileStream(OpenDialog1->FileName, fmOpenRead));
ADOTable1->Insert();
std::unique_ptr<TStream> BlobStream(ADOTable1->CreateBlobStream(ADOTable1->FieldByName("Image"), bmWrite));
BlobStream->CopyFrom(FileStream.get(), FileStream->Size);
BlobStream.reset();
ADOTable1->Post();
}
无论哪种方式,您都应该进行一些错误处理,以便您可以 Cancel()
插入新行,如果在 Post()
之前发生意外情况,例如:
if (OpenDialog1->Execute()) {
std::unique_ptr<TFileStream> FileStream(new TFileStream(OpenDialog1->FileName, fmOpenRead));
ADOTable1->Insert();
try {
std::unique_ptr<TStream> BlobStream(ADOTable1->CreateBlobStream(ADOTable1->FieldByName("Image"), bmWrite));
BlobStream->CopyFrom(FileStream.get(), FileStream->Size);
BlobStream.reset();
ADOTable1->Post();
}
catch (const Exception &) {
ADOTable1->Cancel();
throw;
}
}
当使用以下代码时,我成功地将图像保存到“图像”blob 字段中:
if (OpenDialog1->Execute()) {
ADOTable1->Insert();
TStream* BlobStream = ADOTable1->CreateBlobStream(ADOTable1->FieldByName("Image"), bmWrite);
std::unique_ptr<TFileStream> FileStream(new TFileStream(OpenDialog1->FileName, fmOpenRead));
BlobStream->CopyFrom(FileStream.get(), FileStream->Size);
delete BlobStream;
ADOTable1->Post();
}
但是,我也希望使用 std:unique_ptr
创建 BlobStream
对象,这样我就可以避免手动 delete
。当我尝试
if (OpenDialog1->Execute()) {
ADOTable1->Insert();
std::unique_ptr<TStream> BlobStream(ADOTable1->CreateBlobStream(ADOTable1->FieldByName("Image"), bmWrite));
std::unique_ptr<TFileStream> FileStream(new TFileStream(OpenDialog1->FileName, fmOpenRead));
BlobStream->CopyFrom(FileStream.get(), FileStream->Size);
ADOTable1->Post();
}
我收到 无法插入空行 错误。我在这里做错了什么?我正在使用 C++ Builder 10.3.3。
在原始代码中,您在调用 根据 http://docwiki.embarcadero.com/Libraries/en/Data.Win.ADODB.TADOBlobStream.Destroy Destroy [ie, the destructor] performs the following tasks: Sets the field's data. Changes the field object's Modified property to true. Triggers a field change event in the field's dataset object. Calls the inherited destructor. 因此,您在 在更新的代码中,当 为了确保 blob 无论哪种方式,您都应该进行一些错误处理,以便您可以 Post()
.[=33= 之前 delete
正在 调用 blob TStream
对象 ]
TADOBlobStream
文档:
Post()
之前设置了 blob 的字段数据,一切都很好。BlobStream
超出范围 在 调用 Post()
。因此,尚未设置字段数据,因此出现错误。TStream
对象在调用 Post()
之前被销毁,您可以:
BlobStream
周围放置一个新范围:if (OpenDialog1->Execute()) {
std::unique_ptr<TFileStream> FileStream(new TFileStream(OpenDialog1->FileName, fmOpenRead));
ADOTable1->Insert();
{
std::unique_ptr<TStream> BlobStream(ADOTable1->CreateBlobStream(ADOTable1->FieldByName("Image"), bmWrite));
BlobStream->CopyFrom(FileStream.get(), FileStream->Size);
}
ADOTable1->Post();
}
BlobStream
上手动调用 reset()
:if (OpenDialog1->Execute()) {
std::unique_ptr<TFileStream> FileStream(new TFileStream(OpenDialog1->FileName, fmOpenRead));
ADOTable1->Insert();
std::unique_ptr<TStream> BlobStream(ADOTable1->CreateBlobStream(ADOTable1->FieldByName("Image"), bmWrite));
BlobStream->CopyFrom(FileStream.get(), FileStream->Size);
BlobStream.reset();
ADOTable1->Post();
}
Cancel()
插入新行,如果在 Post()
之前发生意外情况,例如:if (OpenDialog1->Execute()) {
std::unique_ptr<TFileStream> FileStream(new TFileStream(OpenDialog1->FileName, fmOpenRead));
ADOTable1->Insert();
try {
std::unique_ptr<TStream> BlobStream(ADOTable1->CreateBlobStream(ADOTable1->FieldByName("Image"), bmWrite));
BlobStream->CopyFrom(FileStream.get(), FileStream->Size);
BlobStream.reset();
ADOTable1->Post();
}
catch (const Exception &) {
ADOTable1->Cancel();
throw;
}
}