Posts: 246
Threads: 44
Joined: May 2022
Reputation:
28
I tried passing *.* and *.? and similar as a string by Command$ into my program. But instead of the expected string with these three characters, I got a file listing in the form of a long string. I could also use this if...the individual file names were somehow separated. I did a parsing of the obtained string before posting this question here - everything is separated by plain space (CHR 32). This is completely unuseless for, because then you don't know if what you are reading is the continuation of the file name in which there is a space, or if it is the name of another file...
So - of course, from the start I was counting on direntry.h to give me the filenames, that works great - but - how to get the literal mask string *.* or ?????.* and so on? Having Command$ filter it out for me would only be useful if there were special ASC separators in the filenames it provides, like CHR$ 13 or ther characters (which can't be part of a filename)
Posts: 733
Threads: 30
Joined: Apr 2022
Reputation:
43
You can access each individual file in the COMMAND$ by using COMMAND$(n).
Code: (Select All) For i = 1 to _CommandCount
Print Command$(i)
Next
Tread on those who tread on you
Posts: 246
Threads: 44
Joined: May 2022
Reputation:
28
That's great! Thanks a lot!
Posts: 733
Threads: 30
Joined: Apr 2022
Reputation:
43
You are very welcome. I hope that solves your issue
Tread on those who tread on you
Posts: 1,586
Threads: 59
Joined: Jul 2022
Reputation:
52
(03-17-2023, 05:13 PM)Petr Wrote: So - of course, from the start I was counting on direntry.h to give me the filenames, that works great - but - how to get the literal mask string *.* or ?????.* and so on?
This was already discussed in another thread.
https://qb64phoenix.com/forum/showthread.php?tid=1327
It depends very much on the operating system because it intercepts * and ? offered on its command line. This could be CMD.EXE on Windows, or the Powershell equivalent, or "bash" on Linux. Nothing could be done about it. That's why pieces of text that have any * or ? are changed into at least one filename which has neither of those characters, and more likely, it is changed into many filenames.
The filenames without * and ? are received by COMMAND$(). There is no way to get them including * and ?, because MS-DOS worked this way too. If you really, really need to get them you will have to choose substitute characters, for example plus + for stars *. Then, in your program, change the plusses to stars and process it how you want. However, the moment you change to * or ? and then try to use another system call about filenames you will be sent back to what was already discussed about the operating system's filename expansion.
"glob" could be probably disabled in Linux but it's a messy affair. A search produced this:
http://unix.stackexchange.com/questions/...ddg#388697
Posts: 1,586
Threads: 59
Joined: Jul 2022
Reputation:
52
This does some v____o or something else, no need to check for newlines or anything like that, the business is already expanded if using wildcards!
But try using + instead of * and ~ instead of ? in this example.
Code: (Select All) $CONSOLE:ONLY
OPTION _EXPLICIT
REDIM parm(1 TO 1) AS STRING
DIM AS INTEGER v, i
DIM a$, blk$
v = 1
FOR i = 1 TO _COMMANDCOUNT
a$ = COMMAND$(i)
IF INSTR(a$, "+") THEN
ReplaceString2 a$, "+", "*", 0
ELSEIF INSTR(a$, "~") THEN
ReplaceString2 a$, "~", "?", 0
END IF
parm(v) = a$
v = v + 1
REDIM _PRESERVE parm(1 TO v) AS STRING
NEXT
'without "console:only" the user could set this to CHR$(219) for the solid block
blk$ = CHR$(124)
FOR i = 1 TO v - 1
PRINT "Parameter #"; i; " : "; blk$; parm(i); blk$
NEXT
SYSTEM
SUB ReplaceString2 (tx AS STRING, sfind AS STRING, repl AS STRING, numtimes AS _UNSIGNED LONG)
DIM s AS STRING, t AS STRING, goahead AS _BYTE
DIM AS _UNSIGNED LONG ls, count, u
IF (tx = "") OR (sfind = "") OR (sfind = repl) OR (LEN(sfind) > LEN(tx)) THEN EXIT SUB
s = UCASE$(sfind)
t = UCASE$(tx)
ls = LEN(s)
count = 0
goahead = 1
DO
u = INSTR(t, s)
IF u > 0 THEN
tx = LEFT$(tx, u - 1) + repl + MID$(tx, u + ls)
t = UCASE$(tx)
IF numtimes > 0 THEN count = count + 1: IF count >= numtimes THEN goahead = 0
ELSE
goahead = 0
END IF
LOOP WHILE goahead
END SUB
Posts: 246
Threads: 44
Joined: May 2022
Reputation:
28
Thank you very much for your help. On the contrary, it is a welcome help that Command$ saves work and returns filtered files. The above procedure with _CommandCount is excellent and perfectly fine, so I could delete my own sorting solution for the mask and rely on the output from Command$.
I know that mask from the days of Dos, I have worked in Dos since version 5.0, I clearly remember the configurations of Autoexec.bat and Config.sys and at that time the loading of high memory managers EMM386 and Himem.sys and also the booting of CD-Rom drivers under dos it was something as mscdex.exe - something... , yeah that was fun. But there is one more question. *.* should list folders and subdirectories if I remember correctly. Command$ won't do that. Is there a trick to get those subdirectories out of it? If it doesn't work out like this, I'll take a different approach, I'm just asking. I am working on upgrading my PMF2 program.
Posts: 1,586
Threads: 59
Joined: Jul 2022
Reputation:
52
(03-18-2023, 08:56 AM)Petr Wrote: But there is one more question. *.* should list folders and subdirectories if I remember correctly. Command$ won't do that. Is there a trick to get those subdirectories out of it? If it doesn't work out like this, I'll take a different approach, I'm just asking. I am working on upgrading my PMF2 program.
It will have to be done the "direntry.h" way. (The original C header file on Linux is called "dirent.h".) I'm not familiar with it but there should be a field in the structure which helps the programmer tell if the file is a "regular" file or if it's a directory. If it's a directory then you'll have to get another list of files for that directory. It's best to keep track of directories into a string array, as they are found and, after one directory is processed for the file names it has, take it out of the array.
Might want to look at this:
https://qb64phoenix.com/forum/showthread.php?tid=68
Understandably, "*.*" is limited only to the current directory because if could involve thousands of files in subdirectories, and this could choke certain command-line programs and other programs which are not well-written.
|