以下是引用kiff在2017-2-25 11:36:31的发言:
Str1 = "12345人发可个方和方经品他三方登山泛水多福多寿辅导费对方012345678901nLen1-1456789"
nLen1=32
?SUBSTRC(LEFT(str1,nLen1),1)
还可以这样的。
你的是遇到取的最后1位是双字节的第1位时,舍去。
4楼是遇到取的最后1位是双字节的第1位时,取多1位。
把你的和4楼的整合起来,就可以选择最后1为是舍去还是保留了。或者用7楼
整合后如下:
CLEAR
Str1 = "123456人发可个方和方经品他三方登山泛水多福多寿辅导费对方012345678901nLen1-1456789"
nLen1=31
? CutStr(str1,nLen1,0)
? CutStr(str1,nLen1,1)
? _CutStr(str1,nLen1,0)
? _CutStr(str1,nLen1,1)
*!* ======================================
*!* 先计算最后1位是双字节的第1位还是第2位
*!* 根据选择是舍弃还是保留最后1位的双字节
*!* ======================================
FUNCTION CutStr(cStr1,nLen1,nAdd)
LOCAL N1,cStr2
*!* 强行将参数值转换为字符串,并去掉字符串右边的空格
cStr1 = RTRIM(TRANSFORM(cStr1))
*!* 长度参数错误或者大于字符串长度,取字符串最大长度
N1 = LEN(cStr1)
nLen1 = IIF(TYPE("nLen1") # "N",N1,IIF(nLen1>N1,N1,nLen1))
*!* 截取的最后一个字符是半个双字节时,是舍去还是保留
nAdd = IIF(TYPE("nAdd") # "N",0,IIF(nAdd = 1,1,0))
if N1 > nLen1
LOCAL i,nCount
nCount = 0
*!* 计算字符是双字节还是单字节,是第1位还是第2位
FOR i=1 TO nLen1
IF ISLEADBYTE(SUBSTR(cStr1,i,1)) = .T. &&判断双字节时计数 +1
nCount = nCount + 1
ENDIF
ENDFOR
IF ISLEADBYTE(SUBSTR(cStr1,i,1)) = .T. &&判断是不是双字节
IF MOD(nCount,2)=0 &&判断是否双字节的第2位
cStr2=SUBSTR(cStr1,1,nLen1)
ELSE
cStr2=IIF(nAdd = 0,SUBSTR(cStr1,1,nLen1-1),SUBSTR(cStr1,1,nLen1+1))
ENDIF
ELSE
cStr2=SUBSTR(cStr1,1,nLen1)
ENDIF
ELSE
cStr2 = cStr1
ENDIF
RETURN cStr2
ENDFUNC
*! ========================================================
*!* 利用4楼和10方法整合后,可以选择舍去还是保留最后1位双字节
*! ========================================================
FUNCTION _CutStr(cStr1,nLen1,nAdd)
LOCAL nCount,N1
*!* 强行将参数值转换为字符串,并去掉字符串右边的空格
cStr1 = RTRIM(TRANSFORM(cStr1))
*!* 长度参数错误或者大于字符串长度,取字符串最大长度
N1 = LEN(cStr1)
nLen1 = IIF(TYPE("nLen1") # "N",N1,IIF(nLen1>N1,N1,nLen1))
*!* 截取的最后一个字符是半个双字节时,是舍去还是保留
nAdd = IIF(TYPE("nAdd") # "N",0,IIF(nAdd = 1,1,0))
IF nAdd = 0
RETURN SUBSTRC(LEFT(cStr1,nLen1),1)
ELSE
nCount = 0
DO WHILE nCount < nLen1
nCount = nCount + IIF(ISLEADBYTE(SUBSTR(cStr1,nCount+1,1)), 2, 1)
ENDDO
RETURN LEFT(cStr1,nCount)
ENDIF
ENDFUNC
[此贴子已经被作者于2017-2-25 12:16编辑过]