高分求救,一个超难字符串的分解!

redwh 2002-12-26 01:46:47
怎样拆分如下计算公式字符串:

(市场A表(29,3)+市场B表(30,3)+市场C表(31,3))*[2000]+市场C表(31,5)/[1000]

首先我要从这个表达式中读出“市场A表(29,3)”,“市场B表(30,3)”。。。然后到表格中找到对应的数值,然后带入表达式中计算楚结果。

我搞了好久了,怎么都找不到规律!请大家帮个忙,分可以再加!谢了!
...全文
31 21 打赏 收藏 转发到动态 举报
写回复
用AI写文章
21 条回复
切换为时间正序
请发表友善的回复…
发表回复
redwh 2002-12-27
  • 打赏
  • 举报
回复
关于字符串计算的问题很好解决。
function TForm1.Calculate(Expression: string): string;
var
vScript: Variant;
begin
vScript := CreateOleObject('ScriptControl');
vScript.Language := 'JavaScript';
// vScript.Language := 'VBScript';
Result := vScript.Eval(Expression);
end;
procedure TForm1.Button1Click(Sender: TObject);
begin
showmessage(Calculate(edit1.Text));
end;
dyf2001 2002-12-27
  • 打赏
  • 举报
回复
对了如果第一个字符为'[',则不进行替换,只是去掉前后'[]'
dyf2001 2002-12-27
  • 打赏
  • 举报
回复
根据运算符号(+、-、*、/)将原始字符串分开,去掉前边有'(',后边去掉多余')'剩一个。然后到表中查询数据回来替换调原始字符串,现在得到计算公式,只是是字符串,怎么计算还是个问题,你自己考虑吧
redwh 2002-12-27
  • 打赏
  • 举报
回复
var
TempString:String;
FList,LastList:Tstrings;
i:integer;
begin
FList:=TstringList.Create;
LastList:=TstringList.Create;
TempString := '市场A表(29,3)+(市场B表(30,3)+市场C表(31,3))*[2000]+市场C表(31,5)/[1000]';
ExtractStrings(['+','-','*','/'], [], pchar(TempString), FList);//使用运算符号来拆分串
LastList.Clear;
for i:=0 to FList.Count-1 do
begin
{中括号为常量表达式,不参与分解}
if pos('[',Flist[i])=0 then
LastList.Add(FList[i]);
end;
end;
剩下的就容易了:D

给分!
binriyue 2002-12-27
  • 打赏
  • 举报
回复
建义把
(市场A表(29,3)+市场B表(30,3)+市场C表(31,3))*[2000]+市场C表(31,5)/[1000]
改成
(市场A表[29,3]+市场B表[30,3]+市场C表[31,3])*2000+市场C表[31,5]/1000
然后用:
/**
*@decription: 获取表达式的值.
*@param value : 待计算的字符串表达式
*@return : 字符串表达式的值.
*/
function getValue(String value):float
var
strLeft,strTemp,strMid,strRight:String;
dblTemp:float;
begin
int intIndexLeft;//最后一个“(”在字符串value 中的位置
int intIndexRight;//第一个")"在字符串value中的位置.

intIndexLeft = lastIndexOf(value,'(');//取得左括号的索引
if ( intIndexLeft = 0 ) then//value中不存在括号.
begin
if pos('市场', value) then
result := getCellValue(value);
else
result := parseValue(value);
end
else
begin
intIndexRigh = STRPOS(COPY(value,intIndexLeft,length(value)),')');//获取与左括号相匹配的右括号。
//将表达式分成 左 中 右三串
strLeft = STRPOS(value,0,intIndexLeft);//取左串
strTemp = STRPOS(value,intIndexLeft+1,intIndexRight);//取中串
try
dblTemp = parseValue(strTemp);//计算中串的值.
except
//计算出错
end;
strMid = floattostr(dblTemp);//得到新的中串
strRight= STRPOS(value,intIndexRight+1,length(value));//获取右串
value = strLeft + strMid + strRight;//重新组合字符串表达式 .
getValue(value);//递归计算.
} //end else
return result;
end;

//取得最后一个分隔字符所在位置
function lastIndexOf(String sourceStr; String strSplit):Integer
var
sourceStr :String;
begin
str := 'afsdfaasdfsdfadfsfasfdsf';
result := pos(strSplit, sourceStr);
while pos(strSplit, sourceStr)<>0 do
begin
result := pos(strSplit, sourceStr);
sourceStr1 := copy(sourceStr,result,length(sourceStr));//得到部分sourceStr
sourceStr := copy(sourceStr1);//删掉第一个分隔符前的sourceStr
end;
end;

function getCellValue(String StrCell):float
begin
//查询数据表
end;

function parseValue(String:strValue):float
begin
//对字符串进行计算
end;
redwh 2002-12-27
  • 打赏
  • 举报
回复
to dyf2001(西风) :

你的思路非常正确,解决后给分!
redwh 2002-12-27
  • 打赏
  • 举报
回复
to killers100(哈哈)

这里面有'+','-','*','/',括号也是有的有用,有的无用,你的办法是不行的。

to 沙隆拔斯:

你没有考虑括号的问题。


dyf2001 2002-12-27
  • 打赏
  • 举报
回复
那不就行了吗

1、根据运算符号(+、-、*、/)将原始字符串分解为StringList1
(市场A表(29,3)
市场B表(30,3)
市场C表(31,3))
[2000]
市场C表(31,5)
[1000]
2、去除多于扩号得到StringList2
市场A表(29,3)
市场B表(30,3)
市场C表(31,3)
[2000]
市场C表(31,5)
[1000]
3、如果不是以'['开头,查找数据,以'['开头则去除'[]',得到StringList3
data1
data2
data3
2000
data4
1000
4、根据StringList1和String3替换原始字符串,得到字符串
(data1+data2+data3)*2000+data4/1000

5、计算
b51 2002-12-26
  • 打赏
  • 举报
回复
用 加号分开,不就可以了吗
t99 2002-12-26
  • 打赏
  • 举报
回复
呵呵,写得有此乱
t99 2002-12-26
  • 打赏
  • 举报
回复
procedure TForm1.Button1Click(Sender: TObject);
var
temp,TempString,MidString:string;
FormalString:TStringList;
OpString:TStringList; //操作符是顺序的列表列表;
beginIndex,i:integer;
begin
beginIndex := 0;
FormalString := TStringList.Create;
OpString := TStringList.create;
TempString := '市场A表(29,3)+市场B表(30,3)+市场C表(31,3))*[2000]+市场C表(31,5)/[1000]';
temp := tempstring;
for i:=0 to Length(temp) - 1 do
begin
if MidChr(temp[i]) then //比较涵数
begin
OpString.add(temp[i]);
MidString := MidStrings(Temp,beginIndex,i); //组合字符串;
FormalString.Add(MidString);//需要的公式项目在此;
BeginIndex := i;
end;
end;
MidString := Copy(temp,BeginIndex+1,Length(temp)-BeginIndex);

end;

//组合字符串;
function TForm1.MidStrings(CurrString:string;BeginIndex,Index:integer):String;
var
resultString:String;
begin
if BeginIndex = 0 then
resultstring := Copy(CurrString,1,index-1)
else
resultstring := Copy(CurrString,BeginIndex+1,(Index-1)-BeginIndex);
result := resultstring;
end;

//判断是否为分隔符
function TForm1.MidChr(CurrString:String):Boolean;
begin
result := false;
if (CurrString = '+') or (currString = '-') or (currString = '*') or (currString = '/') then
result := true
end;
killers100 2002-12-26
  • 打赏
  • 举报
回复
1、调用这个函数就实现了把其分成“市场A表(29,3)”,“市场B表(30,3)”....的功能,
2、然后再把这个函数再改一下(干脆改成多一个参数输入找的是什么字符算了),调用找出小括号里的两个数字
3、然后调用找出逗号,就接着分解出数字了。
over
给分
killers100 2002-12-26
  • 打赏
  • 举报
回复
都是加号吗??那有办法,我贴上的是我原来写的找出空格的算法
function Readparameter(source :String;j: Integer):String;
var
position: Integer;
I: Integer;
begin
{参数source为须读入大字符串,J为第几个字符串}
position:=pos(' ',source);{空格的位置}
if j=1 then
Result:=(copy(source,0,position-1))
else if j>1 then
begin
//找到第J-1个空格
For I:=1 To j-1 do
begin
position:=pos(' ',source);{空格的位置}
source:=copy(source,position+1,Length(source));
end;
//读取第J个字符串
position:=pos(' ',source);{空格的位置}
Result:=Copy(source,0,position-1);
end
else
Result:='';
end;
wjlsmail 2002-12-26
  • 打赏
  • 举报
回复
是不是又一个个的转换为数值类型 ,再计算 ? 那不是很麻烦 ??

如你得到 '1 + 1 ' ,又要将其分解开 转换为数值型 ;但 字符串中的运算符怎么转换为实际运算符 ?
wjlsmail 2002-12-26
  • 打赏
  • 举报
回复
(市场A表(29,3)+市场B表(30,3)+市场C表(31,3))*[2000]+市场C表(31,5)/[1000]

首先我要从这个表达式中读出“市场A表(29,3)”,“市场B表(30,3)”。。。然后到表格中找到对应的数值,

-----------------------------------------

字符串查找、替换都可以,但 得到的结果字符串(真正要计算的表达式的字符串格式) 怎么转换为 求值表达式 ?

Study
redwh 2002-12-26
  • 打赏
  • 举报
回复
分不够可以再加。
redwh 2002-12-26
  • 打赏
  • 举报
回复
to Drate(鸟窝里的虫) :
如果可以换成别的格式,不就不用问了吗:D
我手里有一个程序它已经实现了啊,可是就是不知道是怎么实现的!
redwh 2002-12-26
  • 打赏
  • 举报
回复
to chutian(我很丑???) :
你的办法太死了,不是所有的公式都是一个样子的啊
chutian 2002-12-26
  • 打赏
  • 举报
回复
S := (市场A表(29,3)+市场B表(30,3)+市场C表(31,3))*[2000]+市场C表(31,5)/[1000];
SubStr1 := 市场B表(30,3);
SubStr2 := 市场A;
SubStr3 := 市场C表(30,3);
...

Val := 市场B表(30,3) -> Value;
...

AnsiReplaceStr(S, SubStr1, FloatToStr(Val));
...

找一個表達式解析器傳入參數 S;
Drate 2002-12-26
  • 打赏
  • 举报
回复
连眼睛看都找不到规律,还想用计算机实现连人脑都做不好的事吗?

难!

有没有办法在生成这个计算公式的字符串的时候就用一个比较容易标识的办法?
加载更多回复(1)

2,498

社区成员

发帖
与我相关
我的任务
社区描述
Delphi 数据库相关
社区管理员
  • 数据库相关社区
加入社区
  • 近7日
  • 近30日
  • 至今
社区公告
暂无公告

试试用AI创作助手写篇文章吧