Sometimes, in my app, I would like to create a copy of a file that already exist, but I don't want to test if the file already exist, I want only that a copy of that file be created, like Windows 7 do.
E.g.: A file tips.txt. When my app copy it, another file will be created named tips - copy.txt. After, if necessary, a "copy of a copy" tips - copy - copy.txt.
Is there something that I can do in this situation?
Obs: in this app, I am using .NET 3.5 and WPF.
Obs2: I made this question because I thought already existed something similar in .NET.
You should extract the filename and the extension then do a simple File.Copy with a new formatted name
string fileName = "tips.txt";
string file = Path.GetFileNameWithoutExtension(fileName);
string ext = Path.GetExtension(fileName);
File.Copy(fileName, string.Format("{0} - Copy{1}", file, ext);
things get a bit more complicated if you have a fullpath to copy from
string fileName = "C:\\test\\tips.txt";
string path = Path.GetDirectoryName(fileName);
string file = Path.GetFileNameWithoutExtension(fileName);
string ext = Path.GetExtension(fileName);
File.Copy(fileName, Path.Combine(path, string.Format("{0} - Copy{1}", file, ext));
but if you really want to mimic the behavior of Windows Explorer we should do:
string fileName = "C:\\test\\tips.txt";
string path = Path.GetDirectoryName(fileName);
string file = Path.GetFileNameWithoutExtension(fileName);
string ext = Path.GetExtension(fileName);
if(file.EndsWith(" - Copy")) file = file.Remove(0, file.Length - 7);
string destFile = Path.Combine(path, string.Format("{0} - Copy{1}", file, ext));
int num = 2;
while(File.Exists(destFile))
{
destFile = Path.Combine(path, string.Format("{0} - Copy ({1}){2}", file, num, ext));
num++;
}
File.Copy(fileName, destFile);
If Windows Explorer copies a file that ends with " - Copy", it adds a progressive number to destination file, not another " - Copy".
You should also consider that the string 'Copy' is localized and thus it changes in non-english version of the operating system.
In addition to other answers suggesting the usage of classes in the System.IO namespace if you want to get the exact same semantics as Windows Copy dialog, you could use the IFileOperation COM object. And here's a managed wrapper for it.
Not sure if this is exactly what you mean, but:
string fileName = "tips.txt";
File.Copy(fileName, string.format("{0} - copy", fileName);
Or:
File.Copy(fileName, string.format("{0} - copy{1}",
Path.GetFileNameWithoutExtension(fileName),
Path.GetExtension(fileName));
You can use File.Copy
http://msdn.microsoft.com/en-us/library/9706cfs5.aspx
What about :
public static void CopyFileLikeWin7(string pathIn,string fileName, string pathOut)
{
string potentialFileName = Path.Combine(pathOut,fileName);
if(File.Exists(potentialFileName))
{
CopyFileLikeWin7(pathIn, Path.GetFileNameWithoutExtension(fileName) + "-copy" + Path.GetExtension(fileName), pathOut);
}
else
{
File.Copy(pathIn,potentialFileName);
}
}
How about
string fileName = "tips.txt";
string filenamewithoutext = Path.GetFileNameWithoutExtension(fileName);
string ext = Path.GetExtension(fileName);
File.Copy(fileName, string.format("{0} - Copy{1}", filenamewithoutext, ext);
Ok, do not test. Just copy the file and don't handle exception
try
{
File.Copy("","");
}
finally
{
}
Something like this? I think there is plenty of more simple ways in doing this.
string destination = "";
var fileInfo = new FileInfo(#"c:\temp\tips.txt");
var ext = fileInfo.Extension;
var filename = fileInfo.Name.Remove(fileInfo.Name.Length - 4);
File.Copy(fileInfo.FullName, destination + filename + " - Copy" + ext);
regarding Steve answer ("but if you really want to mimic the behaviour of Windows Explorer we should do:"), that I've found very useful, I have one comment:
The line:
if (file.EndsWith(" - Copy")) file = file.Remove(0, file.Length - 7);
Should be changed to:
if (file.EndsWith(" - Copy")) file = file.Remove(file.LastIndexOf(" - Copy"), file.Length - 7);
,since in case file ends with " - Copy" we loose the file name and remain with only the "Copy"(s).
Related
i wrote this code , it ctreates folder named "Fitness50" each time but the text file is not created.i want to create textfile within this folder and then save values of an arraylist.
so for i have tried this
DirectoryInfo myDir = new DirectoryInfo(#"E:");
ParentFolderName1 = "Fittness50";
myDir.CreateSubdirectory(ParentFolderName1);
myDir = new DirectoryInfo(ParentFolderName1);
ParentFolderName1 = "Fittness50";
myDir.CreateSubdirectory(ParentFolderName1);
FileName1 = "./" + "" + ParentFolderName1 + "" + "/" + "Fittness10" + "" + "" + PopulationID + "" + ".txt";
FileStream fs2 = new FileStream(FileName1, FileMode.Create, FileAccess.Write);
StreamWriter SW2 = new StreamWriter(fs2);
for (i = 0; i < AlTargetData.Count; i++)
{
SW2.WriteLine(AlTargetData[i]);
}
AlTargetData.Clear();
SW2.Close();
fs2.Close();
Well, first of all, / is not the preferred directory separator on Windows, but \ is. Just because / happens to work, there's no reason to use it. Secondly, you're not creating the Fittness10 folder at all, but you're creating Fittness50 twice. And third, you're not writing the file to the folders you create, but to the current working directory ..
Your code (or at least what I understand you want to achieve) can be shortened significantly to this:
string path = #"E:\Fittness50\Fittness10";
if (!Directory.Exists(path))
Directory.CreateDirectory(path);
string fileName = Path.Combine(path, String.Format("{0}.txt", PopulationID));
File.WriteAllText(fileName, String.Join(Environment.NewLine, AlTargetData));
Please note that you should not consider writing to bin\debug. There will be no bin\debug on the end-user's machine. If the user installs your application, it will be most probably be installed in the Program Files folder, which your application won't be allowed to write to. Instead, consider writing to a common location, like the ones you can chose from in Environment.GetFolderPath.
I have two folders as part of my project, in the folder "Images" is a file called "FingerprintScan.jpg". What I am trying to do is fetch this file and then save it in my other folder called "FingerPrints".
The code I am using does not throw any errors and as far as I can tell should logically work however nothing happens.
string fileName = "FingerprintScan.JPG";
string newfilename = TextBoxUsername.Text + LabelStudentID.Text + ".JPG";
string appPath1 = AppDomain.CurrentDomain.BaseDirectory + #"Images\";
string appPath2 = AppDomain.CurrentDomain.BaseDirectory + #"FingerPrints\";
string sourceFile = System.IO.Path.Combine(appPath1, fileName);
string destFile = System.IO.Path.Combine(appPath2, newfilename);
System.IO.File.Copy(sourceFile, destFile, true);
I have tried playing around and using #"~\Images\ and #"Images but had no luck.
Try this combination and make sure your directory name and source file name match with the physical directory and file
string appPath1 = AppDomain.CurrentDomain.BaseDirectory + "Images";
string appPath2 = AppDomain.CurrentDomain.BaseDirectory + "FingerPrints";
How should I put files paths in a StreamReader array that located in a specific dir C#?
I tried this code in different ways but I didn`t got nothing of what I need and I need one path
string fileName = "myfile.ext";
string path1 = #"mydir";
string path2 = #"\mydir";
string fullPath;
fullPath = Path.GetFullPath(path1);
Console.WriteLine("GetFullPath('{0}') returns '{1}'",
path1, fullPath);
fullPath = Path.GetFullPath(fileName);
Console.WriteLine("GetFullPath('{0}') returns '{1}'",
fileName, fullPath);
fullPath = Path.GetFullPath(path2);
Console.WriteLine("GetFullPath('{0}') returns '{1}'",
path2, fullPath);
Not clear what you're trying to do, but maybe you want a list of files in a folder to a text file? If so, you could use this code:
static void SaveFileListingToText(string folder, string outputTxtFilePath)
{
string[] files = System.IO.Directory.GetFiles(folder);
System.IO.File.WriteAllLines(outputTxtFilePath, files);
}
I have four resource files embedded in my C# executable, 1 python script and 3 perl scripts. I could extract all three perl scripts successfully. But I am not able to extract the python script. I tried so many ways. Could someone please have a look ? Thank you.
public static string ExtractResource(string resourceName)
{
string destFile = "";
//look for the resource name
foreach (string currentResource in System.Reflection.Assembly.GetExecutingAssembly().GetManifestResourceNames() )
if (currentResource.LastIndexOf(resourceName) != -1)
{
string subPath = Common_Utilities.GetTempPath() + "SCRIPTS";
bool isExists = System.IO.Directory.Exists(subPath);
if (!isExists)
System.IO.Directory.CreateDirectory(subPath);
string strFile = subPath + "\\" + resourceName;
string path = System.IO.Path.GetDirectoryName(strFile);
string rootName = System.IO.Path.GetFileNameWithoutExtension(strFile);
destFile = path + #"\" + rootName + System.IO.Path.GetExtension(currentResource);
System.IO.Stream fs = System.Reflection.Assembly.GetExecutingAssembly().GetManifestResourceStream( currentResource ) ;
byte[] buff = new byte[fs.Length];
fs.Read(buff, 0, (int)fs.Length);
fs.Close();
System.IO.FileStream destStream = new System.IO.FileStream(destFile, FileMode.Create);
destStream.Write(buff, 0, buff.Length);
destStream.Close();
}
return destFile;
// throw new Exception("Resource not found : " + resourceName);
}
Not sure why the Python script can't be extracted.... couple points though:
I would recommend to use Path.Combine() to stick together path and file name - don't do this yourself, too many chances for error!
Since those are (text-based) scripts, you could do the whole copying much simpler:
System.IO.Stream fs = System.Reflection.Assembly.GetExecutingAssembly().GetManifestResourceStream(currentResource);
string scriptContents = new StreamReader(fs).ReadToEnd();
File.WriteAllText(destFile, scriptContents);
With this approach, you should be easily able to see in debugging whether or not the script is properly loaded from resources. If not - check your resource name etc. (is the script really set to "embedded" resource?). If you have subdirectories for your resources, be aware that the resource name will contain those subdirectories as part of the fully qualified name - but separated by a dot (.), not a backslash like a physical path!
easy way you can mod your code with
Binary files -> File.WriteAllBytes(Path, Properties.Resources.filename);
Text files -> File.WriteAllText(Path, Properties.Resources.filename);
I have an issue with the reading a file in C#
I have two different locations for .exe (both different) and reading the same .xml file. So when I give the path like this:
TextReader textReader = new StreamReader(#"../../../TrajectoryGen/obstacleList.xml");
it is able to read from one location ( which is 3 folders behind as used in the path) but not from another location (which is only 2 folders behind)
How do I fix this problem so that it works from both folders?
First way, this relies on you knowing one of the parent folder's names.
const string FILENAME = "obstacleList.xml";
const string FOLDER = "TrajectoryGen";
string path = Path.GetFullPath(System.Reflection.Assembly.GetExecutingAssembly().Location);
do
{
path = Path.GetDirectoryName(path);
} while (!Path.GetFileName(path).Equals(FOLDER, StringComparison.OrdinalIgnoreCase));
string filepath = String.Format("{0}{1}{2}", path, Path.DirectorySeparatorChar, FILENAME);
^^ You can also use a partial path in the FILENAME like the example below incase you need to into directories once you are at your "base" folder that you know the name of.
Second way blindly continues up directories
const string FILENAME = #"TrajectoryGen\obstacleList.xml";
string path = Path.GetFullPath(System.Reflection.Assembly.GetExecutingAssembly().Location);
string filepath;
do
{
path = Path.GetDirectoryName(path);
//pump
filepath = String.Format("{0}{1}{2}", path, Path.DirectorySeparatorChar, FILENAME);
} while (!File.Exists(filepath));
Both require "using System.IO;" and both have no error handling implemented and will throw NullReferenceException if the file/folder is not found.
I purposely used the do-while loop because the definition of path will included the executable name.