【问题标题】:Insert a pipe delimiter after every 39 characters每 39 个字符后插入一个管道分隔符
【发布时间】:2019-04-09 17:39:56
【问题描述】:

originally 询问了我需要删除空格并用管道分隔符替换为 13 个空格的问题。我现在有一个不同的文件,其中包含 1 行非常长的文本,我需要在其中插入管道“|”每 39 个字符后的分隔符。我正在尝试使用的文本示例:

000/042 BS CALIFORNIA             90001000/042 BS CALIFORNIA             90002000/042 BS CALIFORNIA             90003000/042 BS CALIFORNIA             90004000/042 BS CALIFORNIA 

我打算编写一个可以执行此操作的批处理文件,因为如果不使用 SSIS 和适当的分隔符对其进行预处理,我将无法将其加载到任何 sql 服务器。任何帮助表示赞赏。

编辑: 替换空格并使文件易于使用的代码如下:

Set Inp = wscript.Stdin
Set Outp = wscript.Stdout
Set regEx = New RegExp
regEx.Pattern = "\s{2,}"
regEx.IgnoreCase = True
regEx.Global = True
Outp.Write regEx.Replace(Inp.ReadAll, "|")

我不确定如何修改它,以便在每 39 个字符之后放置一个管道分隔符。

【问题讨论】:

  • 奇怪的是,您无法将固定文本文件加载到数据库中。我的数据库团队每天都使用 SSIS 包为我做这件事。
  • 谢谢壁球手。也许我对 SSIS 也有点无能。

标签: batch-file cmd vbscript ssis fixed-width


【解决方案1】:

感谢大家关注这个问题。我发布的解决方案对我来说已经足够了。最初的意图是在每 39 个字符后插入一个管道分隔符。但我在想一个不同的方向。我可以使用 SSIS 平面文件源完成相同的任务,其中我将格式选项选择为“固定宽度”并根据需要加载数据。

【讨论】:

    【解决方案2】:
    Set Inp = wscript.Stdin
    Set Outp = wscript.Stdout
    Set regEx = New RegExp
    regEx.Pattern = "(.{39,39})"
    regEx.IgnoreCase = True
    regEx.Global = True
    Outp.Write regEx.Replace(Inp.ReadAll, "$1|")
    

    http://download.microsoft.com/download/winscript56/Install/5.6/W982KMeXP/EN-US/scrdoc56en.exe

    是 VBScript 帮助文件。查找 pattern 属性。 . 除换行符外的任何字符,最小 39 和最大 39,$1 替换为我们找到的内容加上管道。

    【讨论】:

      【解决方案3】:

      这里是基于my answeryour original question 代码的解决方案。以下脚本再次使用相同的技术来克服通常适用于批处理文件的行长度限制(请参阅代码中的所有解释性 rem 注释):

      @echo off
      setlocal EnableExtensions DisableDelayedexpansion
      
      rem // Define constants here:
      set "_INPUT=.\PXZP_SND_XZ01_GFT10553.dat" & rem // (this is the input file)
      set "_OUTPUT=.\R1.txt" & rem // (set to `con` to display the result on the console)
      set "_TEMPF=%TEMP%\%~n0_%RANDOM%.tmp" & rem // (specifies a temporary file)
      set /A "_FIX=39" & rem // (this specifies the fixed width)
      set "_INSERT=|"  & rem // (this is the insertion string)
      rem // This stores an end-of-file character in a variable:
      for /F %%E in ('forfiles /P "%~dp0." /M "%~nx0" /C "cmd /C echo 0x1A"') do set "_EOF=%%E"
      
      rem /* The input file is going to be processed in a sub-routine,
      rem    which accesses the file content via input redirection `<`: */
      < "%_INPUT%" > "%_OUTPUT%" call :PROCESS
      
      endlocal
      exit /B
      
      
      :PROCESS
          rem // Reset variables that store a partial string to be processed and a separator:
          set "PART=" & set "SEP="
          setlocal EnableDelayedExpansion
      :READ
          rem /* At this point 1023 characters are read from the input file at most, until
          rem    a line-break or the end of the file is encountered:*/
          set "NEW=" & set /P NEW=""
          rem // The read characters are appended to a string buffer that will be processed:
          set "PART=!PART!!NEW!"
      :LOOP
          rem // Check whether or not the string buffer is empty:
          if defined PART (
              rem // String buffer is not empty, so split it in two parts using the fixed width:
              set "LEFT=!PART:~,%_FIX%!" & set "RIGHT=!PART:~%_FIX%!"
          ) else (
              rem /* String buffer is empty, hence reset both left and right string portions;
              rem    this step is necessary since splitting an empty string is not possible: */
              set "LEFT=" & set "RIGHT="
          )
          rem /* Jump back to read more characters in case the right string portion is empty,
          rem    unless the end of the file has already been reached, hence no more are left: */
          if not defined RIGHT if defined NEW goto :READ
          rem /* Skip processing when the left string portion is empty, which is the case when
          rem    no more data are left, so when the end of the file has already been reached: */
          if defined LEFT (
              rem /* Write to a temporary file the output string, which consists of an insertion
              rem    string (except for the very first time), the left string portion and an
              rem    end-of-file character; a line-break is automatically appended by `echo`: */
              > "!_TEMPF!" echo(!SEP!!LEFT!%_EOF%
              rem /* Copy the temporary file onto itself, but remove the end-of-file character
              rem    and everything after, then type the file content; this is a safe way of
              rem    echoing a string without a trailing line-break: */
              > nul copy /Y /A "!_TEMPF!" + nul "!_TEMPF!" /B & type "!_TEMPF!"
              rem // Set the insertion string now to skip it only for the first output:
              set "SEP=!_INSERT!"
              rem // Move the right string portion into the string buffer:
              set "PART=!RIGHT!"
              rem // Jump back to process the updated string buffer, hence to split it again:
              goto :LOOP
          )
          endlocal
          rem // Clean up the temporary file:
          del "%_TEMPF%"
          exit /B
      

      请注意,给定的固定宽度必须是小于大约 8190 个字符的正数。

      【讨论】:

        猜你喜欢
        • 1970-01-01
        • 2017-08-24
        • 2020-04-25
        • 2023-02-25
        • 1970-01-01
        • 2011-03-16
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        相关资源
        最近更新 更多