Skip to content

Commit d620489

Browse files
committed
[*]Fix empty function
1 parent c74a22c commit d620489

7 files changed

Lines changed: 95 additions & 5 deletions

File tree

dist/lib/common.js

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -46,6 +46,7 @@ function getExpectTypeByToken(prevTokenItem) {
4646
switch (curSubType) { // 查看起始和结束
4747
case token_1.TokenSubType.SUBTYPE_START:
4848
expectTypeList = [
49+
[token_1.TokenType.TYPE_SUBEXPR, token_1.TokenSubType.SUBTYPE_STOP],
4950
[token_1.TokenType.TYPE_SUBEXPR, token_1.TokenSubType.SUBTYPE_START],
5051
[token_1.TokenType.TYPE_SET, token_1.TokenSubType.SUBTYPE_START],
5152
[token_1.TokenType.TYPE_FUNCTION, null],

dist/lib/token.js

Lines changed: 12 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -112,12 +112,12 @@ function parseLineToken(formulaStr, line, lastTokenItem, lastParentTokenTypeList
112112
* @return {ITokenItem} 令牌对象
113113
*/
114114
function parseType(formula, prevTokenItem) {
115-
var curParentType = prevTokenItem.parentType;
116115
var expectTypeList = common_1.getExpectTypeByToken(prevTokenItem);
117116
var tokenItem = parseFormulaStr(formula, expectTypeList);
118117
// 如果是结束符时,设置当前类型为父类型
119118
if (tokenItem && tokenItem.subType === token_1.TokenSubType.SUBTYPE_STOP) {
120-
tokenItem.type = curParentType;
119+
// 检测前一个类型是否为闭合直接设置父类型或
120+
tokenItem.type = isParentToken(prevTokenItem) ? prevTokenItem.type : prevTokenItem.parentType;
121121
}
122122
return {
123123
expectTypeList: expectTypeList,
@@ -212,6 +212,16 @@ function isClosedToken(tokenItem) {
212212
}
213213
return false;
214214
}
215+
// 是否为父级元素
216+
function isParentToken(tokenItem) {
217+
switch (tokenItem.type) {
218+
// 以下类型需要特殊判断
219+
case token_1.TokenType.TYPE_FUNCTION:
220+
case token_1.TokenType.TYPE_SUBEXPR:
221+
return true;
222+
}
223+
return false;
224+
}
215225
/**
216226
* 以下为各个匹配数据类型函数
217227
*/

package.json

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,6 @@
11
{
22
"name": "func-formula-parser",
3-
"version": "0.1.3",
3+
"version": "0.1.4",
44
"description": "a AST parser for formula & formula function",
55
"main": "dist/index.js",
66
"types": "src/index.d.ts",

src/lib/common.ts

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -48,6 +48,7 @@ export function getExpectTypeByToken(prevTokenItem: ITokenItem): ExpectType[] {
4848
switch (curSubType) { // 查看起始和结束
4949
case TokenSubType.SUBTYPE_START:
5050
expectTypeList = [
51+
[TokenType.TYPE_SUBEXPR, TokenSubType.SUBTYPE_STOP], // 函数结束符,空函数
5152
[TokenType.TYPE_SUBEXPR, TokenSubType.SUBTYPE_START], // 子表达式
5253
[TokenType.TYPE_SET, TokenSubType.SUBTYPE_START], // 集合起始
5354
[TokenType.TYPE_FUNCTION, null],

src/lib/token.ts

Lines changed: 13 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -121,12 +121,12 @@ function parseType(formula: string, prevTokenItem: ITokenItem): {
121121
expectTypeList: ExpectType[],
122122
item: ITokenItem
123123
} {
124-
const curParentType = prevTokenItem.parentType;
125124
const expectTypeList: ExpectType[] = getExpectTypeByToken(prevTokenItem);
126125
const tokenItem = parseFormulaStr(formula, expectTypeList);
127126
// 如果是结束符时,设置当前类型为父类型
128127
if (tokenItem && tokenItem.subType === TokenSubType.SUBTYPE_STOP) {
129-
tokenItem.type = curParentType;
128+
// 检测前一个类型是否为闭合直接设置父类型或
129+
tokenItem.type = isParentToken(prevTokenItem) ? prevTokenItem.type : prevTokenItem.parentType;
130130
}
131131
return {
132132
expectTypeList,
@@ -226,6 +226,17 @@ function isClosedToken(tokenItem: ITokenItem): boolean {
226226
return false;
227227
}
228228

229+
// 是否为父级元素
230+
function isParentToken(tokenItem: ITokenItem): boolean {
231+
switch (tokenItem.type) {
232+
// 以下类型需要特殊判断
233+
case TokenType.TYPE_FUNCTION:
234+
case TokenType.TYPE_SUBEXPR:
235+
return true;
236+
}
237+
return false;
238+
}
239+
229240
/**
230241
* 以下为各个匹配数据类型函数
231242
*/

test/lib/node.test.js

Lines changed: 39 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -264,6 +264,45 @@ module.exports = function() {
264264
});
265265
});
266266
describe('Function', function() {
267+
it('IF(Empty(),-count(3,4,5),5%)', function() {
268+
formulaParser.setFormula('IF(Empty(),-count(3,4,5),5%)');
269+
const assertNodeTree = {
270+
token: 'IF',
271+
children: [
272+
{
273+
token: 'Empty'
274+
},
275+
{
276+
token: '-',
277+
children: [
278+
{
279+
token: 'count',
280+
children: [
281+
{
282+
token: '3'
283+
},
284+
{
285+
token: '4'
286+
},
287+
{
288+
token: '5'
289+
}
290+
]
291+
}
292+
]
293+
},
294+
{
295+
token: '%',
296+
children: [
297+
{
298+
token: '5'
299+
}
300+
]
301+
}
302+
]
303+
};
304+
validTokenReulst(formulaParser.getNodeTree(), assertNodeTree);
305+
});
267306
it('IF(a>=0,-count(3,4,5),5%)', function() {
268307
formulaParser.setFormula('IF(a>=0,-count(3,4,5),5%)');
269308
const assertNodeTree = {

test/lib/token.test.js

Lines changed: 28 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -388,6 +388,34 @@ module.exports = function() {
388388
});
389389
});
390390
describe('Function', function() {
391+
it('Empty()', function() {
392+
const tokenList = formulaParser.setFormula('Empty()');
393+
const assertResult = [
394+
{
395+
parentType: null,
396+
type: TOKEN.TokenType.TYPE_FUNCTION,
397+
subType: TOKEN.TokenSubType.SUBTYPE_START,
398+
token: 'Empty',
399+
row: 1,
400+
start: 0,
401+
end: 6,
402+
sourceStart: 0,
403+
sourceEnd: 6
404+
},
405+
{
406+
parentType: null,
407+
type: TOKEN.TokenType.TYPE_FUNCTION,
408+
subType: TOKEN.TokenSubType.SUBTYPE_STOP,
409+
token: '',
410+
row: 1,
411+
start: 6,
412+
end: 7,
413+
sourceStart: 6,
414+
sourceEnd: 7
415+
}
416+
];
417+
validTokenReulst(tokenList, assertResult);
418+
});
391419
it('Round(-1, -5%)', function() {
392420
const tokenList = formulaParser.setFormula('Round(-1, -5%)');
393421
const assertResult = [

0 commit comments

Comments
 (0)