{"id":64403,"date":"2007-07-21T00:58:00","date_gmt":"2007-07-21T00:58:00","guid":{"rendered":"https:\/\/blogs.technet.microsoft.com\/heyscriptingguy\/2007\/07\/21\/how-can-i-delete-specified-characters-from-the-beginning-and-end-of-my-file-names\/"},"modified":"2007-07-21T00:58:00","modified_gmt":"2007-07-21T00:58:00","slug":"how-can-i-delete-specified-characters-from-the-beginning-and-end-of-my-file-names","status":"publish","type":"post","link":"https:\/\/devblogs.microsoft.com\/scripting\/how-can-i-delete-specified-characters-from-the-beginning-and-end-of-my-file-names\/","title":{"rendered":"How Can I Delete Specified Characters From the Beginning and End of My File Names?"},"content":{"rendered":"<p><IMG class=\"nearGraphic\" title=\"Hey, Scripting Guy! Question\" height=\"34\" alt=\"Hey, Scripting Guy! Question\" src=\"https:\/\/devblogs.microsoft.com\/wp-content\/uploads\/sites\/29\/2019\/02\/q-for-powertip.jpg\" width=\"34\" align=\"left\" border=\"0\"> \n<P>Hey, Scripting Guy! How can I truncate file names by removing a common beginning and ending, leaving only the unique middle portion of the name?<BR><BR>&#8212; RE <\/P><IMG height=\"5\" alt=\"Spacer\" src=\"https:\/\/devblogs.microsoft.com\/scripting\/wp-content\/uploads\/sites\/29\/2019\/05\/spacer.gif\" width=\"5\" border=\"0\"><IMG class=\"nearGraphic\" title=\"Hey, Scripting Guy! Answer\" height=\"34\" alt=\"Hey, Scripting Guy! Answer\" src=\"https:\/\/devblogs.microsoft.com\/wp-content\/uploads\/sites\/29\/2019\/02\/a-for-powertip.jpg\" width=\"34\" align=\"left\" border=\"0\"><A href=\"http:\/\/go.microsoft.com\/fwlink\/?linkid=68779&amp;clcid=0x409\"><IMG class=\"farGraphic\" title=\"Script Center\" height=\"288\" alt=\"Script Center\" src=\"http:\/\/img.microsoft.com\/library\/media\/1033\/technet\/images\/scriptcenter\/ad.jpg\" width=\"120\" align=\"right\" border=\"0\"><\/A> \n<P>Hey, RE. Before we answer your question we\u2019d like to point out that we\u2019ve finally <A href=\"http:\/\/www.microsoft.com\/technet\/scriptcenter\/topics\/teched07\/winners.mspx\"><B>posted the winners<\/B><\/A> of the Scripting Guys <A href=\"http:\/\/www.microsoft.com\/technet\/scriptcenter\/topics\/teched07\/challenge.mspx\"><B>TechEd Challenge<\/B><\/A>. (If you <I>are<\/I> a winner we\u2019ve got good news: our shipping materials have arrived, which means that, at long last, your prizes are out the door and on the way.) We\u2019ve also posted one possible solution to the puzzle, a solution the Scripting Guys came up with and \u2013 we add proudly \u2013 a solution that would have earned us a perfect score of 140 points. Wasn\u2019t it really, really hard to come up with a perfect score? No, of course not. Not for the Scripting Guys anyway.<\/P>\n<TABLE class=\"dataTable\" id=\"ELD\" cellSpacing=\"0\" cellPadding=\"0\">\n<THEAD><\/THEAD>\n<TBODY>\n<TR class=\"record\" vAlign=\"top\">\n<TD class=\"\">\n<P><B>Note<\/B>. OK, so that <I>might<\/I> be due, in part, to the fact that we cheated: we started with a list of words and then derived the puzzle using that list. But hey, that\u2019s about the only way the Scripting Guys could even <I>hope<\/I> to come up with a perfect score.<\/P>\n<P>And even that took a few tries.<\/P><\/TD><\/TR><\/TBODY><\/TABLE>\n<DIV class=\"dataTableBottomMargin\"><\/DIV>\n<P>When we first posted the challenge we were concerned that people would find it too difficult. \u201cThis is hard,\u201d we thought. \u201cWe need to offer a really big incentive in order to get people to even <I>try<\/I> solving the puzzle.\u201d With that in mind, we made a ridiculous offer that we knew we\u2019d never have to follow up on: if anyone turned in a perfect score, we\u2019d rename the Script Center after them (well, for one day, that is).<\/P>\n<P>Much to our surprise, <I>nine different people<\/I> submitted perfect scores, and some of those people submitted more than one perfect entry. (At some point you\u2019d think we\u2019d learn that just because the Scripting Guys find something to be really, really hard that doesn\u2019t mean that anyone else will find that same task to be even the slightest bit challenging.) To tell you the truth, we weren\u2019t prepared for all those perfect entries. Nevertheless, a deal is a deal, so sometime in the very near future we\u2019ll begin renaming the Script Center in honor of our grand prize winners.<\/P>\n<TABLE class=\"dataTable\" id=\"EHE\" cellSpacing=\"0\" cellPadding=\"0\">\n<THEAD><\/THEAD>\n<TBODY>\n<TR class=\"record\" vAlign=\"top\">\n<TD class=\"\">\n<P><B>Note<\/B>. So how does TechNet feel about us renaming the Script Center in honor of our grand prize winners? Surprisingly enough, TechNet is 100% in favor of this; in fact, the good people at TechNet think that this is by far the best idea the Scripting Guys have ever come up with.<\/P>\n<P>Or at least that\u2019s what they <I>would<\/I> think, provided they actually knew about all this.<\/P>\n<P>Or at least that\u2019s what we think they would think.<\/P><\/TD><\/TR><\/TBODY><\/TABLE>\n<DIV class=\"dataTableBottomMargin\"><\/DIV>\n<P>Now back to RE\u2019s question. RE has a folder that has a series of files with names similar to this:<\/P><PRE class=\"codeSample\">8901 George.txt\nFile 1234 George.txt\nFile 2345 George.txt\nFile 3456 George.txt\nFile 4567 George.txt\nFile 5678 George.txt\nFile 6789 George.txt\nFile 7890.txt\n<\/PRE>\n<P>As you can see, most of the file names start with <B>File <\/B>and then end with <B>George<\/B>; a few files start with <B>File<\/B> but don\u2019t end with <B>George<\/B>, and a few others end with <B>George<\/B> but don\u2019t start with <B>File<\/B>. All the files, however, have a unique \u201cmiddle name;\u201d for example, the file <I>File 1234 George.txt<\/I> has a \u201cmiddle name\u201d of <I>1234<\/I>. What RE would like to do is take that file name and remove the <B>File<\/B> and\/or the <B>George<\/B>, resulting in file names like this:<\/P><PRE class=\"codeSample\">8901.txt\n1234.txt\n2345.txt\n3456.txt\n4567.txt\n5678.txt\n6789.txt\n7890.txt\n<\/PRE>\n<P>How can he do that? Here\u2019s one way:<\/P><PRE class=\"codeSample\">strComputer = &#8220;.&#8221;<\/p>\n<p>Set objWMIService = GetObject(&#8220;winmgmts:\\\\&#8221; &amp; strComputer &amp; &#8220;\\root\\cimv2&#8221;)<\/p>\n<p>Set colFiles = objWMIService.ExecQuery _\n    (&#8220;ASSOCIATORS OF {Win32_Directory.Name=&#8217;C:\\Test&#8217;} Where &#8221; _\n        &amp; &#8220;ResultClass = CIM_DataFile&#8221;)<\/p>\n<p>For Each objFile In colFiles\n    strPath = objFile.Drive &amp; objFile.Path\n    strExtension = objFile.Extension\n    strFileName = objFile.FileName<\/p>\n<p>    If Left(strFileName, 5) = &#8220;File &#8221; Then\n        intLength = Len(strFileName)\n        strFileName = Right(strFileName, intLength &#8211; 5)\n    End If<\/p>\n<p>    If Right(strFileName, 7) = &#8221; George&#8221; Then\n        intLength = Len(strFileName)\n        strFileName = Left(strFileName, intLength &#8211; 7)\n    End If<\/p>\n<p>    strNewName = strPath &amp; strFileName &amp; &#8220;.&#8221; &amp; strExtension\n    errResult = objFile.Rename(strNewName)\nNext\n<\/PRE>\n<P>We actually get quite a few questions similar to this, questions about removing specific bits of text that have been tacked onto the beginning and\/or the end of file names. Because of that, and because that\u2019s what we\u2019re supposed to do in this column anyway, let\u2019s take a few minutes to walk through the code and see if we can figure out what\u2019s going on here.<\/P>\n<P>The script starts out by connecting to the WMI service on the local computer. Could we modify this script to perform the same task against a <I>remote<\/I> computer? You bet we can; to do that, simply assign the name of the remote computer to the variable strComputer:<\/P><PRE class=\"codeSample\">strComputer = &#8220;atl-fs-01&#8221;\n<\/PRE>\n<P>After connecting to the WMI service we then use the following bit of code to return a collection of all the files (instances of the <B>CIM_DataFile<\/B> class) found in the folder C:\\Test:<\/P><PRE class=\"codeSample\">Set colFiles = objWMIService.ExecQuery _\n    (&#8220;ASSOCIATORS OF {Win32_Directory.Name=&#8217;C:\\Test&#8217;} Where &#8221; _\n        &amp; &#8220;ResultClass = CIM_DataFile&#8221;)\n<\/PRE>\n<P>When the collection comes back we set up a For Each loop to loop through all the files in that collection. And then we get down to business.<\/P>\n<P>Admittedly, there are a couple different ways we could go about this task; we\u2019ve opted to use an approach that requires a few extra lines of code but is a little safer to use. What makes it \u201csafer?\u201d Here\u2019s one example. We <I>could<\/I> just use the <B>Replace<\/B> function to replace any instances of target terms <I>File<\/I> and <I>George<\/I> in the file path. So why don\u2019t we? Well, suppose we had a file named <I>File George Washington File George.txt<\/I>. Doing a blank search-and-replace operation would result in this:<\/P><PRE class=\"codeSample\">Washington.txt\n<\/PRE>\n<P>In other words, we would have removed more than just the beginning and the ending. In turn, that means that we could run into name collisions if the folder also included a file named, say, <I>File Washington George.txt<\/I>. Likewise, suppose the folder we\u2019re working with is named <I>Documents From George<\/I>. Removing all instances of <I>George<\/I> would delete the term from the folder path as well, something which would lead to all sorts of trouble. And the Scripting Guys don\u2019t want trouble.<\/P>\n<P>Which is why we didn\u2019t mention that rename-the-Script-Center thing to anyone from TechNet.<\/P>\n<P>At any rate, the first thing we do inside the loop is execute the following three lines of code:<\/P><PRE class=\"codeSample\">strPath = objFile.Drive &amp; objFile.Path\nstrExtension = objFile.Extension\nstrFileName = objFile.FileName\n<\/PRE>\n<P>All we\u2019re doing here is grabbing the individual pieces of the file path. If we have a file named <I>C:\\Test\\File 1234 George.txt<\/I>, that means that our variables will end up being assigned the following values:<\/P>\n<TABLE class=\"dataTable\" id=\"EQH\" cellSpacing=\"0\" cellPadding=\"0\">\n<THEAD><\/THEAD>\n<TBODY>\n<TR class=\"record\" vAlign=\"top\">\n<TD class=\"\">\n<P class=\"lastInCell\"><B>Variable<\/B><\/P><\/TD>\n<TD class=\"\">\n<P class=\"lastInCell\"><B>Value<\/B><\/P><\/TD><\/TR>\n<TR class=\"evenRecord\" vAlign=\"top\">\n<TD class=\"\">\n<P class=\"lastInCell\">strPath<\/P><\/TD>\n<TD class=\"\">\n<P class=\"lastInCell\">C:\\Test\\<\/P><\/TD><\/TR>\n<TR class=\"record\" vAlign=\"top\">\n<TD class=\"\">\n<P class=\"lastInCell\">strExtension<\/P><\/TD>\n<TD class=\"\">\n<P class=\"lastInCell\">txt<\/P><\/TD><\/TR>\n<TR class=\"evenRecord\" vAlign=\"top\">\n<TD class=\"\">\n<P class=\"lastInCell\">strFileName<\/P><\/TD>\n<TD class=\"\">\n<P class=\"lastInCell\">File 1234 George<\/P><\/TD><\/TR><\/TBODY><\/TABLE>\n<DIV class=\"dataTableBottomMargin\"><\/DIV>\n<P>For more information about properties like <B>Drive<\/B> and <B>Path<\/B>, see the <A href=\"http:\/\/www.microsoft.com\/technet\/scriptcenter\/guide\/sas_fil_scfm.mspx\" target=\"_blank\"><B>Microsoft Windows 2000 Scripting Guide<\/B><\/A>.<\/P>\n<P>Our next step is to determine whether or not the file name starts with the characters <I>File<\/I> and, if it does, delete those characters. That\u2019s what this block of code is for:<\/P><PRE class=\"codeSample\">If Left(strFileName, 5) = &#8220;File &#8221; Then\n    intLength = Len(strFileName)\n    strFileName = Right(strFileName, intLength &#8211; 5)\nEnd If\n<\/PRE>\n<P>As you can see, we\u2019re using the <B>Left <\/B>function to determine whether the first five characters in our file name are equal to <I>File<\/I> (note the blank space at the end). Let\u2019s assume that they are. In that case, we then use the <B>Len<\/B> function to determine the number of characters in the string (i.e., the length of the string), storing that value in a variable named intLength:<\/P><PRE class=\"codeSample\">intLength = Len(strFileName)\n<\/PRE>\n<P>That brings us to this line of code:<\/P><PRE class=\"codeSample\">strFileName = Right(strFileName, intLength &#8211; 5)\n<\/PRE>\n<P>This is where we strip the word <I>File<\/I> from the beginning of the string. What we\u2019re doing here is using the <B>Right<\/B> function to grab characters from the <I>end<\/I> of the string, working our way back towards the beginning. How many characters are we going to grab? We\u2019re going to grab the total number of characters in the string, minus 5. And why \u201cminus 5?\u201d That\u2019s easy: this will scoop all the characters in the string <I>except for the first 5<\/I>. In other words, if we have a file named <I>File 1234 George<\/I> strFileName will be assigned the following value:<\/P><PRE class=\"codeSample\">1234 George\n<\/PRE>\n<P>Which means that we\u2019re now halfway towards our goal of truncating the first file name.<\/P>\n<P>We then use a similar process to determine whether the term <I>George<\/I> (again, note the blank space, this time in front of the term) appears at the end of the file name; if so, we go ahead and delete that term as well. That\u2019s what this block of code is for:<\/P><PRE class=\"codeSample\">If Right(strFileName, 7) = &#8221; George&#8221; Then\n    intLength = Len(strFileName)\n    strFileName = Left(strFileName, intLength &#8211; 7)\nEnd If\n<\/PRE>\n<P>What\u2019s the net result of all this? The net result is that strFileName is now equal to the file\u2019s \u201cmiddle name:\u201d<\/P><PRE class=\"codeSample\">1234\n<\/PRE>\n<P>That\u2019s great; this is just what we wanted. However, we still have one problem: when using WMI you can\u2019t rename a file unless you pass the <B>Rename<\/B> method the complete file path. (Which means that simply having a file name of <I>1234<\/I> doesn\u2019t do us much good.) With that in mind, we use the following line of code to construct a new file path, storing that value in the variable strNewName:<\/P><PRE class=\"codeSample\">strNewName = strPath &amp; strFileName &amp; &#8220;.&#8221; &amp; strExtension\n<\/PRE>\n<P>Nothing too fancy here; we\u2019re simply combining the following values:<\/P>\n<TABLE class=\"\" cellSpacing=\"0\" cellPadding=\"0\" border=\"0\">\n<TBODY>\n<TR>\n<TD class=\"listBullet\" vAlign=\"top\">\u2022<\/TD>\n<TD class=\"listItem\">\n<P>C:\\Test\\<\/P><\/TD><\/TR>\n<TR>\n<TD class=\"listBullet\" vAlign=\"top\">\u2022<\/TD>\n<TD class=\"listItem\">\n<P>1234<\/P><\/TD><\/TR>\n<TR>\n<TD class=\"listBullet\" vAlign=\"top\">\u2022<\/TD>\n<TD class=\"listItem\">\n<P>.<\/P><\/TD><\/TR>\n<TR>\n<TD class=\"listBullet\" vAlign=\"top\">\u2022<\/TD>\n<TD class=\"listItem\">\n<P>txt<\/P><\/TD><\/TR><\/TBODY><\/TABLE>\n<P>Put them all together and strNewName ends up with <I>this<\/I> value:<\/P><PRE class=\"codeSample\">C:\\Test\\1234.txt\n<\/PRE>\n<P>And you know what? You\u2019re right: that <I>does<\/I> look an awful lot like a complete file path, doesn\u2019t it? We\u2019re glad you pointed that out, because that means we can go ahead and call the Rename method and actually rename the file:<\/P><PRE class=\"codeSample\">errResult = objFile.Rename(strNewName)\n<\/PRE>\n<P>And then it\u2019s back to the top of the loop, where we repeat this process with the next file in the collection. When all is said and done, the folder C:\\Test will be the proud owner of the following set of files:<\/P><PRE class=\"codeSample\">8901.txt\n1234.txt\n2345.txt\n3456.txt\n4567.txt\n5678.txt\n6789.txt\n7890.txt\n<\/PRE>\n<P>Not bad, not bad at all.<\/P>\n<P>Incidentally, if you liked the TechEd Challenge we will likely have some similar puzzles for you in the near future: we\u2019re currently negotiating with <I>TechNet Magazine<\/I> to create a puzzle for each and every issue. Nothing is set in stone just yet, but we\u2019ll likely end up creating these puzzles for them. Nonetheless, we do expect that the negotiations will be a bit contentious; after all, they pay us absolutely nothing to write the <A href=\"http:\/\/www.microsoft.com\/technet\/scriptcenter\/resources\/tnmag\/archive.mspx\"><B>Hey, Scripting Guy!<\/B><\/A> column for the magazine, and we need an iron-clad guarantee that we\u2019ll get the exact same deal before we agree to start doing puzzles for them as well. <\/P>\n<P>Don\u2019t worry: no one takes advantage of the Scripting Guys.<\/P><\/p>\n","protected":false},"excerpt":{"rendered":"<p>Hey, Scripting Guy! How can I truncate file names by removing a common beginning and ending, leaving only the unique middle portion of the name?&#8212; RE Hey, RE. Before we answer your question we\u2019d like to point out that we\u2019ve finally posted the winners of the Scripting Guys TechEd Challenge. (If you are a winner [&hellip;]<\/p>\n","protected":false},"author":595,"featured_media":87096,"comment_status":"open","ping_status":"closed","sticky":false,"template":"","format":"standard","meta":{"_acf_changed":false,"footnotes":""},"categories":[1],"tags":[3,4,21,5],"class_list":["post-64403","post","type-post","status-publish","format-standard","has-post-thumbnail","hentry","category-scripting","tag-scripting-guy","tag-scripting-techniques","tag-string-manipulation","tag-vbscript"],"acf":[],"blog_post_summary":"<p>Hey, Scripting Guy! How can I truncate file names by removing a common beginning and ending, leaving only the unique middle portion of the name?&#8212; RE Hey, RE. Before we answer your question we\u2019d like to point out that we\u2019ve finally posted the winners of the Scripting Guys TechEd Challenge. (If you are a winner [&hellip;]<\/p>\n","_links":{"self":[{"href":"https:\/\/devblogs.microsoft.com\/scripting\/wp-json\/wp\/v2\/posts\/64403","targetHints":{"allow":["GET"]}}],"collection":[{"href":"https:\/\/devblogs.microsoft.com\/scripting\/wp-json\/wp\/v2\/posts"}],"about":[{"href":"https:\/\/devblogs.microsoft.com\/scripting\/wp-json\/wp\/v2\/types\/post"}],"author":[{"embeddable":true,"href":"https:\/\/devblogs.microsoft.com\/scripting\/wp-json\/wp\/v2\/users\/595"}],"replies":[{"embeddable":true,"href":"https:\/\/devblogs.microsoft.com\/scripting\/wp-json\/wp\/v2\/comments?post=64403"}],"version-history":[{"count":0,"href":"https:\/\/devblogs.microsoft.com\/scripting\/wp-json\/wp\/v2\/posts\/64403\/revisions"}],"wp:featuredmedia":[{"embeddable":true,"href":"https:\/\/devblogs.microsoft.com\/scripting\/wp-json\/wp\/v2\/media\/87096"}],"wp:attachment":[{"href":"https:\/\/devblogs.microsoft.com\/scripting\/wp-json\/wp\/v2\/media?parent=64403"}],"wp:term":[{"taxonomy":"category","embeddable":true,"href":"https:\/\/devblogs.microsoft.com\/scripting\/wp-json\/wp\/v2\/categories?post=64403"},{"taxonomy":"post_tag","embeddable":true,"href":"https:\/\/devblogs.microsoft.com\/scripting\/wp-json\/wp\/v2\/tags?post=64403"}],"curies":[{"name":"wp","href":"https:\/\/api.w.org\/{rel}","templated":true}]}}