locked
Does file exist in win 8 app and c++ ?

    Question

  • How do I create a task for this function and catch if the file doesn't exist ?
    	int fileexist()
    	{
    
    		String^ fileName="arnold.pcb"; 
    	
    	StorageFolder^ item = KnownFolders::PicturesLibrary;
    	
    	try
    	{
    	item->GetFileAsync(fileName);
    	}
    	catch(...)
    	{
    		return 0;
    	}
    
    	return 1;
    
    
    	}


    n.Wright

    Sunday, September 22, 2013 5:21 PM

All replies

  • This was discussed previously.

    Of course, the real question is why are you doing a file exist test in the first place? If you don't need the file, why open it?

    Sunday, September 22, 2013 6:19 PM
  • This was discussed previously.

    Of course, the real question is why are you doing a file exist test in the first place? If you don't need the file, why open it?

    I don't want to try to load the file if it doesn't exist and cause an exception.

    The file holds the status of a game (if it has been saved)

    It might or might not have been saved previously.


    n.Wright

    Sunday, September 22, 2013 6:23 PM
  • But the point is you get told about the file existing or not based on an exception.  A single exception throw here is not going to kill your app performance. The problem would be if you were trying to check for the file existence of hundreds or thousands of files--in which case a better choice is to enumerate all the files in that directory and look for the files you are wanting to check for, not individually open and close every one of those files.

    In this case, a better solution is to try to load your 'save game' and then if it is not present, handle the exception as you'd have to anyhow.

    Generally even with standard Win32 applications, File Exists tests are not very efficient. They trigger all the same Anti-Virus activity and are exactly as much work as opening the file to read in the first place.

    BAD:

    if File Exists
        if Open file succeeded
            Read file
        else
            Handle error
    else
       Handle error
       

    GOOD:

    if Open file succeeded
        Read file
    else
        Handle error (including possibly file not existing)

    BTW, I don't know why you are thinking you'd use the "Pictures Library" to store your 'save game'. Such application state should be stored in Windows::Storage::ApplicationData->LocalFolder or ->RoamingFolder.

    http://msdn.microsoft.com/en-us/library/windows/apps/hh758319.aspx


    Sunday, September 22, 2013 6:30 PM
  • That's exactly the problem I don't know how to handle the exception.

    I have tried various try/catch combinations but I still get "file not found" error popping up.

    In WPF I would just call "Fileexists" function and have a flag I could use.

    It seems async functions are not so easy to try/catch.

    	
    void Renderer::loadgame()
    {
    		String^ fileName="arnold.pcb"; 
    	
    	StorageFolder^ item = KnownFolders::PicturesLibrary;
    
    	auto getFileOp = item->GetFileAsync(fileName);
    	getFileOp->Completed = ref new AsyncOperationCompletedHandler<StorageFile^>
        ([=](IAsyncOperation<StorageFile^>^ operation, AsyncStatus status)
      {
        auto storageFile = operation->GetResults();
    	auto openOp = storageFile->OpenAsync(FileAccessMode::Read);
        openOp->Completed = 
          ref new AsyncOperationCompletedHandler <IRandomAccessStream^>
          ([=](IAsyncOperation<IRandomAccessStream^>^ operation, AsyncStatus status)
        {
          auto istream = operation->GetResults();
          auto dr = ref new DataReader(istream);
          auto loadOp = dr->LoadAsync(istream->Size);
          loadOp->Completed = ref new AsyncOperationCompletedHandler<UINT>
            ([=](IAsyncOperation<UINT>^ operation, AsyncStatus status)
          {
    
    		    auto bytesRead = operation->GetResults();
    
    			time=(UINT32)(dr->ReadUInt32());
    			screennumber=(UINT32)(dr->ReadUInt32());
    
    			dr->DetachStream();
    
    	  
    
    
    			
    		try{
    	operation->GetResults();		//Get the result of task by forcing it.
    		  }
    		  catch(...)
    		  {
    			  return;
    		  }
    
    
    	  });
        });
      });
    


    n.Wright

    Sunday, September 22, 2013 6:35 PM
  • The rest of your application is going to need to function if this fails for any number of reasons.

    Take a look at PPL. It makes handling this async stuff robustly in C++ very easy.

    http://msdn.microsoft.com/en-us/library/windows/apps/Hh780559.aspx

    BTW, for those cases where you really need a synchronous file existence test and there's not a better way to handle it (note the case above is not a good case for this), just use the Win32 API CreateFile2 with OPEN_ALWAYS

    Sunday, September 22, 2013 6:45 PM
  • That worked ok after I disabled first
    int fileexists(String^ fileName)
    {    
        using namespace Windows::Storage;
        using namespace concurrency;
    
        StorageFolder^ PicturesFolder = KnownFolders::PicturesLibrary;
        auto getFileTask = create_task(PicturesFolder->GetFileAsync(fileName));
    
        getFileTask.then([](StorageFile^ storageFileSample)
        {       
    
        })
    
        .then([](task<void> t) 
        {
    
            try
            {
                t.get();
            }
            catch (Platform::COMException^ e)
            {
      return 0;
            }
    
    
    		loadgame();   
    		
        });
    
    
    
    return 1;
    }
    
    

    chance exceptions.

    n.Wright

    Sunday, September 22, 2013 7:10 PM