简体   繁体   中英

In Windows cmd, how to replace the " special character with a line break?

Just to be thorough, I'll state here my whole project and what I'm aiming at.

I intend to adapt a shell script to work in Windows cmd, as this is intended for people who are not going to have some sophisticate language available.

for g in $(curl -Ls https://api.chess.com/pub/player/hikaru/games/archives | jq -rc ".archives[]") ; do curl -Ls "$g" | jq -rc ".games[].pgn" ; done >> games.pgn

For some reason, Chess.com's API doesn't have a very important feature that Lichess' does, to export all games of a single player, so what I can do manually is to use https://api.chess.com/pub/player/hikaru/games/archives to export all available monthly archives and then hit the API for each one of them. ( hikaru inside this will be a set variable, it's the nickname of the desired player to export).

The result for this command is something like

{"archives":["https://api.chess.com/pub/player/hikaru/games/2015/11","https://api.chess.com/pub/player/hikaru/games/2015/12","https://api.chess.com/pub/player/hikaru/games/2016/02","https://api.chess.com/pub/player/hikaru/games/2016/03","https://api.chess.com/pub/player/hikaru/games/2016/04","https://api.chess.com/pub/player/hikaru/games/2016/05"]}

to which I only have to append /pgn to get the desired result.

Obviously, cmd doesn't have jq available, so this involves "parsing" the string inside a batch file.

I figured if I just could replace every occurrence of " with a linebreak and echo the results, I could then use find (or findstr ) to easily get a list of lines that only would need to be prefaced with curl and appended with /pgn to get my final result.

The big question is: how do I replace " with a linebreak in cmd? I found a few answers, but none of them seems to work with a special character, part of the problem is that I also didn't understand these answers enough to try and adapt them.

A second way of perhaps achieving the same result would be replacing [ , ] and , with line breaks, but then I would also have to worry with deleting the final " to append /pgn , so if I'm able to do the former, it would be cleaner.

in batch/cmd, a for loop is used to process a list (separated by default delimiters like space, tab, comma). So just replace [ and ] with a space or comma, and you have a nice list to split. Finally, use find to filter the output to the relevant parts and you're done:

@Echo off
setlocal

set "string={"archives":["https://api.chess.com/pub/player/hikaru/games/2015/11","https://api.chess.com/pub/player/hikaru/games/2015/12","https://api.chess.com/pub/player/hikaru/games/2016/02","https://api.chess.com/pub/player/hikaru/games/2016/03","https://api.chess.com/pub/player/hikaru/games/2016/04","https://api.chess.com/pub/player/hikaru/games/2016/05"]}"


set "string=%string:[= %"
set "string=%string:]= %"
for %%a in (%string%) do echo %%~a|find "/"

Output:

https://api.chess.com/pub/player/hikaru/games/2015/11
https://api.chess.com/pub/player/hikaru/games/2015/12
https://api.chess.com/pub/player/hikaru/games/2016/02
https://api.chess.com/pub/player/hikaru/games/2016/03
https://api.chess.com/pub/player/hikaru/games/2016/04
https://api.chess.com/pub/player/hikaru/games/2016/05

(in case you wonder: the tilde in echo %%~a removes surrounding quotes)

Stephan's answer gave me the directions I needed to research more and build my own solution. This is not the final script to my project, but it does solve every problem presented in my original question:

@echo off
setLocal enabledelayedexpansion
for /f "delims=" %%a in (input.txt) do (
    for %%b in (%%a) do (
    set string=%%b
    set "string=!string:[=,!"
    set "string=!string:]=,!" 
    echo !string!>>replaced.txt
    )
)
for /f "delims=" %%c in (replaced.txt) do (
    for %%d in (%%c) do (
    echo %%~d>>echo.txt
    )
)
for /f %%e in (echo.txt) do echo curl %%~e/pgn|find ".">>list.txt

I basically run 3 sets of loops, the first one loads my input (this could not be done via set because there's a size limit, using a nested loop works around that) and replaces [ and ] for commas.

The second loop sorts again the output. This is done basically to trim unwanted characters from the first and last line.

The last loop generates a list of curl commands that will later be executed into a PGN file (which is a chess file).


This ends the scope of the question, but since my project wasn't that complex, I'll present it's final version, which improves on Compo's answer, in case someone else stumbles upon this question:

:::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::
::             Chess.com and Lichess API Scraper               ::
::                  Author: fabiorzfreitas                     ::
:: Extract all games from a player from Chess.com and Lichess  ::
:::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::

:: This tool uses Chess.com and Lichess APIs to extract all games from a given player. ::

@echo off
setLocal enabledelayedexpansion

echo.
echo.
echo.
echo All input must be lowcase!
echo.
echo You can skip the input bellow by pressing Enter
echo.
echo.
echo.
set /p lichess="Input Lichess nickname and press Enter: "
set /p chess="Input Chess.com nickname and press Enter: "
echo.

:Lichess
if not defined lichess goto :Chess

curl https://lichess.org/api/games/user/%lichess% >> Games.pgn

:Chess
if not defined chess goto :End

(for /f "usebackq tokens=2 delims=[]" %%g in (`curl https://api.chess.com/pub/player/%chess%/games/archives`) do (
    for %%h In (%%g) do curl "%%~h/pgn" >> Games.pgn
    )
)

:End
exit

Based upon your own answer, it seems as if you could remove at least one of those steps by using the brackets [ and ] , as delimiters.

You could also nest a for loop within another instead of having individual ones and writing to files.

Here it is as a single line :

@(For /F "UseBackQ Tokens=2 Delims=[]" %%G In ("input.txt") Do @For %%H In (%%G) Do @Echo curl.exe "%%~H/pgn") 1>"list.txt"

To do it directly in :

(For /F "UseBackQ Tokens=2 Delims=[]" %G In ("input.txt") Do @For %H In (%G) Do @Echo curl.exe "%~H/pgn") 1>"list.txt"

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM