3

私はDICOMファイルを読み取るためのアプリケーションを作成していますが、それを行うには他のライブラリを使用する必要があります。ライブラリはファイルを開きますが、終了時にファイルを閉じません。また、ライブラリはオープンソースではありません。Linux ではオープン ファイルの制限が 1024 であることを知っており、その数を変更できます。しかし、私はそのやり方をしたくありません。ライブラリによって開かれているファイルを閉じるのが好きです。ファイルが開いていることがわかっている場合、Cでファイルを閉じる方法。http://cbi.nyu.edu/software/dinifti.phpから取得した DICOM2NII ライブラリを使用しています。これはファイルを開くコードですが、閉じません

bool DICOMImage::OpenFile(const char *path)
{
    bool retValue = true;
    DCM_Objects handle_;
    unsigned long options = DCM_ORDERLITTLEENDIAN | DCM_FORMATCONVERSION | DCM_VRMASK;
    // Try opening as PART10, if it fails it's might be bcause it does not have
    // a preable and the try it that way
    if ( DCM_OpenFile(path, options | DCM_PART10FILE, &handle_) != DCM_NORMAL )
    {
        DCM_CloseObject(&handle_);
        COND_PopCondition(TRUE);
        if ( DCM_OpenFile(path, options, &handle_) != DCM_NORMAL )
        {    
          retValue = false;
        }
        else
          retValue=true;
    }

    return retValue;
}
4

2 に答える 2

2

DICOMImageクラスにメンバーを追加します

DCM_OBJECT *handle_;

そしてデストラクタでファイルを閉じます

DICOMImage::DICOMImage() : handle_(0) { ... }

DICOMImage::~DICOMImage() {
    if (handle_ != 0)
        DCM_CloseObject(&handle_);
}

もちろん、このメンバーも使用しますhandle_DICOMImage::OpenFile()

于 2013-03-07T08:22:44.287 に答える
1

最初にすべてのファイル記述子をテストして、fcntl(fd, F_GETFD)0 からgetdtablesize(). ライブラリ関数が戻ると、 で閉じることができるもう 1 つの開いている fd がありますclose()。また、以前に開かれていなかったすべてのものを呼び出すこともできclose(fd)、そのうちの 1 つが成功します (検索のその時点で停止できます)。

最初の未使用の fd まで初期プローブを実行できる可能性が高く、ライブラリは、1 つのファイルを開くよりも複雑なことをしない限り、その fd を使用することになります。複数のファイルを開いたり使用dup()したりすると、別の場所に移動する可能性があります。

これを説明するには:

#include <iostream>
#include <vector>
#include <unistd.h>
#include <fcntl.h>

std::vector<bool> getOpenFileMap()
{
    int limit = getdtablesize();
    std::vector<bool> result(limit);

    for (int fd = 0; fd < limit; ++fd)
        result[fd] = fcntl(fd, F_GETFD) != -1;
    return result;
}

void closeOpenedFiles(const std::vector<bool> &existing)
{
    int limit = existing.size();
    for (int fd = 0; fd < limit; ++fd)
        if (!existing[fd])
            close(fd);
}

int getLikelyFd()
{
    int limit = getdtablesize();

    for (int fd = 0; fd < limit; ++fd)
        if (fcntl(fd, F_GETFD) != -1)
            return fd;
}

int main()
{
    std::vector<bool> existing = getOpenFileMap();
    int fd = open("/dev/null", O_RDONLY);
    closeOpenedFiles(existing);
    bool closed = write(fd, "test", 4) == -1;
    std::cout << "complex pass " << std::boolalpha << closed << std::endl;

    int guess = getLikelyFd();
    fd = open("/dev/null", O_RDONLY);
    bool match = fd == guess;
    std::cout << "simple pass " << std::boolalpha << match << std::endl;
}
于 2013-03-07T07:15:08.933 に答える