Visual LISP, AutoLISP and General Customization
cancel
Showing results for 
Show  only  | Search instead for 
Did you mean: 

Need a lisp routine to string-split

19 REPLIES 19
Reply
Message 1 of 20
tomgsd
11160 Views, 19 Replies

Need a lisp routine to string-split

Hi, I am urgently need a lisp route to split a string into a list. Please help, for example, use space as delimit
(string-split " " "dddddddd jjjjjjjj 123454 orueru 4832409 ")
return a list
("dddddddd" "jjjjjjjj" "123454" "orueru" "4832409")


Thanks in advanced.
19 REPLIES 19
Message 2 of 20
Kent1Cooper
in reply to: tomgsd

Here's something I use in a routine that determines a bunch of things about a hatch pattern's definition from the first line-set's definition line. It breaks things up around commas instead of spaces, but the principle is translatable. You can:

1. build a (while) loop to repeat the similar steps as long as there's still some string left;

2. replace hpline1 with a variable name containing your string;

3. change the 44 to the ASCII code for a space [32],
[or replace all the instances of
(vl-string-position 44 ....)
with
(vl-string-search " " ....)]

4. use (cons) to assemble the results into a list, and (reverse) at the end to turn it back into the right order;

5. make other appropriate adjustments [no (atof), for example].

{code}
(setq
hpangdef (atof (substr hpline1 1 (vl-string-position 44 hpline1))); code prior to first comma -- angle of first line set as defined [degrees]
hpang (- hpdir1 (* (/ hpangdef 180) pi)); applied rotation angle of hatch pattern [radians]
hpline1 (substr hpline1 (+ (vl-string-position 44 hpline1) 2)); truncated code line from after first comma
hpXor (atof (substr hpline1 1 (vl-string-position 44 hpline1))); X origin as defined
hpline1 (substr hpline1 (+ (vl-string-position 44 hpline1) 2)); truncated code line from after first comma
hpYor (atof (substr hpline1 1 (vl-string-position 44 hpline1))); Y origin as defined
); end setq
{code}

I can't work that all out for you right now, but if you can't, and no one else does [or offers another solution], I may get to it in a day or two.

--
Kent Cooper


tomgsd wrote...
....need a lisp route to split a string into a list. ... for example, use space as delimit
(string-split " " "dddddddd jjjjjjjj 123454 orueru 4832409 ")
return a list
("dddddddd" "jjjjjjjj" "123454" "orueru" "4832409")
Kent Cooper, AIA
Message 3 of 20
Anonymous
in reply to: tomgsd

{code} ;;++++++++++++++++++
;; parser by CAB
;;++++++++++++++++++
(defun sparser (str delim / ptr lst)
(while (setq ptr (vl-string-search delim str))
(setq lst (cons (substr str 1 ptr) lst))
(setq str (substr str (+ ptr 2)))
)
(reverse (cons str lst))
){code}

{code}_$ (sparser "12,3,4,,5,6," ",")
("12" "3" "4" "" "5" "6" "")
_$ (vl-remove "" (sphraser "12,3,4,,5,6," ","))
("12" "3" "4" "5" "6"){code}
Message 4 of 20
Anonymous
in reply to: tomgsd

This is a rough stab at it, for some reason that I am too tired to figure
out it pulls everything but the last word. Perhaps you can figure out why.

(DEFUN STRING-SPLIT (STR DELM / STR-LIST N TEMP-WORD OUTPUT CNTR3 )

(SETQ CNTR3 1 STR-LIST NIL)
(REPEAT (STRLEN STR)
(SETQ STR-LIST (CONS (ASCII (SUBSTR STR CNTR3 1)) STR-LIST ) CNTR3
(1+ CNTR3))
)
(SETQ STR-LIST (REVERSE STR-LIST) TEMP-WORD "" OUTPUT NIL)
(FOREACH N STR-LIST
(IF (/= N (ASCII DELM))
(SETQ TEMP-WORD (STRCAT TEMP-WORD (CHR N)))
(SETQ OUTPUT (CONS TEMP-WORD OUTPUT ) TEMP-WORD "" )
)
(if (and (= n (length str-list))(/= temp-word "")) (SETQ OUTPUT (CONS
TEMP-WORD OUTPUT ) TEMP-WORD "" ))
)
(reverse output)
)

(STRING-SPLIT
"qqqqqq#wwwwww#sssssss#xxxxxxx#rodney#test#adfgfgr#eeeee#zzzzzzasdfasdf"
"#")


"tomgsd" wrote in message news:6320322@discussion.autodesk.com...
Hi, I am urgently need a lisp route to split a string into a list. Please
help, for example, use space as delimit
(string-split " " "dddddddd jjjjjjjj 123454 orueru 4832409 ")
return a list
("dddddddd" "jjjjjjjj" "123454" "orueru" "4832409")


Thanks in advanced.
Message 5 of 20
NikolayPoleshchuk
in reply to: tomgsd

If upper case fits then for using space as a delimiter:
(setq str "sdsdfgg 3456 jfd 99")
(setq result (mapcar 'vl-princ-to-string (read (strcat "(" str ")"))))
;("SDSDFGG" "3456" "JFD" "99") ;strcased

http://poleshchuk.spb.ru/cad/eng.html
Nikolay Poleshchuk
http://poleshchuk.spb.ru/cad/eng.html
Message 6 of 20
Anonymous
in reply to: tomgsd

{code}

Comando: (vl-remove
(_> ""
(_> (ALE_String2List
((_> "dddddddd jjjjjjjj 123454 orueru 4832409 " " "
((_> )
(_> )
("dddddddd" "jjjjjjjj" "123454" "orueru" "4832409")


; Marc'Antonio Alessi, Italy - http://xoomer.virgilio.it/alessi
;
; Function: ALE_String2List
;
; Version 1.00 - November 2001
;
; Description:
; convert a string into a list
;
; Arguments:
; InpStr = string [STR]
; CarDlm = delimiter [STR] 1 character
;
(defun ALE_String2List (InpStr CarDlm / SttPos EndPos TmpLst)
(setq
CarDlm (ascii CarDlm) SttPos 0
EndPos (vl-string-position CarDlm InpStr)
)
(while EndPos
(setq
TmpLst (cons (substr InpStr (1+ SttPos) (- EndPos SttPos)) TmpLst)
SttPos (1+ EndPos) EndPos (vl-string-position CarDlm InpStr SttPos)
)
)
(reverse (cons (substr InpStr (1+ SttPos)) TmpLst))
)

{code}

--
Marc'Antonio Alessi
http://xoomer.virgilio.it/alessi
GPS: N45° 50' 16" E12° 22' 44"
--
"tomgsd" ha scritto nel messaggio news:6320322@discussion.autodesk.com...
Hi, I am urgently need a lisp route to split a string into a list. Please
help, for example, use space as delimit
(string-split " " "dddddddd jjjjjjjj 123454 orueru 4832409 ")
return a list
("dddddddd" "jjjjjjjj" "123454" "orueru" "4832409")


Thanks in advanced.
Message 7 of 20
Anonymous
in reply to: tomgsd

This works if you don't mind the conversion to upper case.

{code}

(setq lin "dddddddd jjjjjjjj 123454 orueru 4832409")

(setq lin (mapcar 'vl-princ-to-string (read (strcat "(" lin ")"))) ;list of strings.
)

("DDDDDDDD" "JJJJJJJJ" "123454" "ORUERU" "4832409")

{code}

If it upper case is not desired, you can convert it back like this:
{code}
(mapcar '(lambda(x)(strcase x t)) lin)

("dddddddd" "jjjjjjjj" "123454" "orueru" "4832409")

{code}

Edited by: BillZndl on Jan 19, 2010 8:51 AM

Opps, I see NikolayPoleshchuk already posted last night. Edited by: BillZndl on Jan 19, 2010 10:25 AM
Message 8 of 20
stevor
in reply to: tomgsd

Try this easy to employ way:
(setq ListOfSubStrs (pars_s OriginalBigStr ) )

[code]
; parse refstr by deLimstr in to List of strs
(defun pars_s (rs / L i a b Q n)
(if (and rs (= 'STR (type rs)) (setq Q (strLen rs) i 1 d " "))
(whiLe (<= i Q)
(whiLe (and (= (substr rs i 1) d) (<= i Q)) (setq i (1+ i)) )
(setq n i)
(whiLe (and (/= (substr rs i 1) d) (<= i Q)) (setq i (1+ i)) )
(setq a (substr rs n (- i n)) i (1+ i) )
(if (and a (/= "" a)) (setq L (cons a L)))) )
(if L (reverse L)) )
[code]
S
Message 9 of 20
tomgsd
in reply to: tomgsd

Thanks, I tried this one. It works excellent except it treats multiple space as a element "" in the list. I think I can use it after normalizing the original str to one-space only.
Message 10 of 20
tomgsd
in reply to: tomgsd

This one is even better. Because I use space as delimit. It is exactly what I want. It deals with multiple space as one space. Thanks a lot!!!
Message 11 of 20
Anonymous
in reply to: tomgsd

How about DOSLib's DOS_STRTOKENS function.

For example:

Command: (dos_strtokens "dddddddd jjjjjjjj 123454 orueru 4832409 "
" " T)
("dddddddd" "jjjjjjjj" "123454" "orueru" "4832409")

http://www.en.na.mcneel.com/doslib.htm

- Dale

"tomgsd" wrote in message news:6320322@discussion.autodesk.com...
> Hi, I am urgently need a lisp route to split a string into a list. Please
> help, for example, use space as delimit
> (string-split " " "dddddddd jjjjjjjj 123454 orueru 4832409 ")
> return a list
> ("dddddddd" "jjjjjjjj" "123454" "orueru" "4832409")
>
>
> Thanks in advanced.
Message 12 of 20
Anonymous
in reply to: tomgsd

I thought that DOS_STRTOKENS was much faster...

Benchmark.lsp | © 2005 Michael Puckett | All Rights Reserved

(setq astring "dddddddd jjjjjjjj 123454 orueru 4832409 ")
(Benchmark
'(
(dos_strtokens astring " " T)
(vl-remove "" (ALE_String2List astring " "))
)

Elapsed milliseconds / relative speed for 16384 iteration(s):

(VL-REMOVE "" (ALE_STRING2LIST ASTRING).....1030 / 1.24
(DOS_STRTOKENS ASTRING " " T)..........................1279 / 1



;-)

--
Marc'Antonio Alessi
http://xoomer.virgilio.it/alessi
GPS: N45° 50' 16" E12° 22' 44"
--
{code}
"Dale Fugier" ha scritto nel messaggio
news:6320941@discussion.autodesk.com...
How about DOSLib's DOS_STRTOKENS function.

For example:

Command: (dos_strtokens "dddddddd jjjjjjjj 123454 orueru 4832409 "
" " T)
("dddddddd" "jjjjjjjj" "123454" "orueru" "4832409")

http://www.en.na.mcneel.com/doslib.htm

- Dale

"tomgsd" wrote in message news:6320322@discussion.autodesk.com...
> Hi, I am urgently need a lisp route to split a string into a list. Please
> help, for example, use space as delimit
> (string-split " " "dddddddd jjjjjjjj 123454 orueru 4832409 ")
> return a list
> ("dddddddd" "jjjjjjjj" "123454" "orueru" "4832409")
>
>
> Thanks in advanced.
Message 13 of 20
Anonymous
in reply to: tomgsd

Maybe this is better:

{code}
; Marc'Antonio Alessi, Italy - http://xoomer.virgilio.it/alessi
;
; Function: ALE_String_ToList
;
; Version 1.00 - 01/2010
;
; Description:
; convert a string into a list of strings
;
; Arguments:
; InpStr = string [STR]
; CarDlm = delimiter [STR] 1 character
; TrueFl = if nil remove dupes delimiter
;
; Examples:
; (ALE_String_ToList "aaa_vvv_hhh__yyy ___lll_" "_" T)
; ("aaa" "vvv" "hhh" "" "yyy " "" "" "lll" "lll")
;
; (ALE_String_ToList "aaa_vvv_hhh__yyy ___lll_" "_" nil)
; ("aaa" "vvv" "hhh" "yyy " "lll")
;
(defun ALE_String_ToList (InpStr CarDlm TrueFl / SttPos EndPos TmpLst
TmpStr)
(setq
CarDlm (ascii CarDlm) SttPos 0
EndPos (vl-string-position CarDlm InpStr)
)
(while EndPos
(setq
TmpStr (substr InpStr (1+ SttPos) (- EndPos SttPos))
SttPos (1+ EndPos) EndPos (vl-string-position CarDlm InpStr SttPos)
)
(and
(or TrueFl (/= TmpStr ""))
(setq TmpLst (cons TmpStr TmpLst))
)
)
(if (or TrueFl (/= (setq TmpStr (substr InpStr (1+ SttPos))) ""))
(reverse (cons TmpStr TmpLst))
(reverse TmpLst)
)
)
{code}
Message 14 of 20
Anonymous
in reply to: tomgsd

...hummmm..
..
{code}
; Marc'Antonio Alessi, Italy - http://xoomer.virgilio.it/alessi
;
; Function: ALE_String_ToList
;
; Version 1.00 - 01/2010
;
; Description:
; convert a string into a list of strings
;
; Arguments:
; InpStr = string [STR]
; CarDlm = delimiter [STR] 1 character
; TrueFl = if nil remove dupes delimiter
;
; Examples:
; (ALE_String_ToList "aaa_vvv_hhh__yyy ___lll_" "_" T)
; ("aaa" "vvv" "hhh" "" "yyy " "" "" "lll")
;
; (ALE_String_ToList "aaa_vvv_hhh__yyy ___lll_" "_" nil)
; ("aaa" "vvv" "hhh" "yyy " "lll")
;
(defun ALE_String_ToList (InpStr CarDlm TrueFl / SttPos EndPos TmpLst
TmpStr)
(setq
CarDlm (ascii CarDlm) SttPos 0
EndPos (vl-string-position CarDlm InpStr)
)
(while EndPos
(and
(or (/= (setq TmpStr (substr InpStr (1+ SttPos) (- EndPos SttPos)))"")
TrueFl)
(setq TmpLst (cons TmpStr TmpLst))
)
(setq SttPos (1+ EndPos) EndPos (vl-string-position CarDlm InpStr
SttPos))
)
(if (or (/= (setq TmpStr (substr InpStr (1+ SttPos))) "") TrueFl)
(reverse (cons TmpStr TmpLst))
(reverse TmpLst)
)
)
{code}
Message 15 of 20
CADaSchtroumpf
in reply to: tomgsd

Hi,

My contribution
{code}
(defun string-split (string pattern / l_pat tmp nw_pat)
(cond
((and (eq (type string) 'STR) (eq (type pattern) 'STR) (eq (strlen string) 1))
(setq l_pat (vl-string->list pattern))
(while l_pat
(if (not (eq (car l_pat) (ascii string)))
(setq tmp (cons (car l_pat) tmp))
(if tmp (setq nw_pat (cons (reverse tmp) nw_pat) tmp nil))
)
(setq l_pat (cdr l_pat))
)
(if tmp (setq nw_pat (cons (reverse tmp) nw_pat) tmp nil))
(mapcar 'vl-list->string (reverse nw_pat))
)
(T (princ "*Incorrect argument*")(prin1))
)
)
{code}
Message 16 of 20
iciubotariu
in reply to: tomgsd

Other previous solutions make the division of the string only to the space character, in this solution we can select any other character:

 

(defun splitchr (str ch)
(setq kk 1
lst1 (list)
)
(while (<= kk (strlen str))
(setq chr "")
(while (and (/= (substr str kk 1) ch)(<= kk (strlen str)))
(setq chr (strcat chr (substr str kk 1)))
(setq kk (+ 1 kk))
)
(setq lst1 (append lst1 (list chr) ))
(setq kk (+ 1 kk))

)
)

;;; exemple: (splitchr "cdscsd,vfdvdfv dfv, dssdcv" ",")

;;; return lst1-> ("cdscsd" "vfdvdfv dfv" "dssdcv")

 

Message 17 of 20
hencoop
in reply to: tomgsd

Robert McNeel & Associates free product DOSLIB does this nicely.

dos_strtokens.jpg

AutoCAD User since 1989. Civil Engineering Professional since 1983
Product Ver.: 13.6.1781.0 Civil 3D 2024.3 Update
Built On:        U.152.0.0 AutoCAD 2024.1.2
                        27.0.37.14 Autodesk AutoCAD Map 3D 2024.0.1
                        8.6.52.0 AutoCAD Architecture 2024
Message 18 of 20
john.uhden
in reply to: hencoop

Here's what I use...

  ;;---------------------------------------------------------
  ;; Function to convert a string with delimiters into a list
  ;; pat is the delimiter and can contain multiple characters
  (defun @str2list (str pat / i j n lst)
     (cond
        ((/= (type str)(type pat) 'STR))
        ((= str pat)'(""))
        (T
           (setq i 0 n (strlen pat))
           (while (setq j (vl-string-search pat str i))
             (setq lst (cons (substr str (1+ i)(- j i)) lst)
                   i (+ j n)
             )
           )
           (reverse (cons (substr str (1+ i)) lst))
         )
      )
   )

John F. Uhden

Message 19 of 20
hencoop
in reply to: hencoop

P.S  I contacted McNeal & Associates some years ago about licensing DOSLIB for use within commercial products.

They informed me that DOSLIB may be included in any user's commercial products without royalty or fee.  DOSLIB contains a treasure of library routines that will greatly simplify your programming effort so you can move on to the specific coding that only you can provide for your routines.

 

AutoCAD User since 1989. Civil Engineering Professional since 1983
Product Ver.: 13.6.1781.0 Civil 3D 2024.3 Update
Built On:        U.152.0.0 AutoCAD 2024.1.2
                        27.0.37.14 Autodesk AutoCAD Map 3D 2024.0.1
                        8.6.52.0 AutoCAD Architecture 2024
Tags (1)
Message 20 of 20
john.uhden
in reply to: hencoop

Your research is correct.

John F. Uhden

Can't find what you're looking for? Ask the community or share your knowledge.

Post to forums  

Autodesk Design & Make Report

”Boost