Advertisement
Not a member of Pastebin yet?
Sign Up,
it unlocks many cool features!
- package com.appypie.snappy.appsheet.asformula
- import android.text.TextUtils.split
- import android.util.Log
- import android.util.SparseArray
- import com.appypie.snappy.appsheet.extensions.isDigitsOnly
- import com.appypie.snappy.appsheet.pagedata.model.FieldItem
- import com.facebook.internal.Mutable
- import java.util.*
- import kotlin.collections.ArrayList
- object FormulaUtil {
- var squareBracesRegex = "\\[[^\\[]*\\]"
- var stackTokenArr: MutableList<String>? = null
- var strTst = "CONCATENATE(UPPER([FName]),[LName],LOWER([FName]))" //"CONCATENATE(UPPER([FName]),[LName],LOWER([FName]),UPPER([FName]))"
- var txtFunctionArr = arrayOf("LEN", "LEFT", "RIGHT", "TRIM", "CONCATENATE", "FIND", "UPPER", "LOWER")
- var operatorArr = arrayOf("+", "-", "/", "%", "*")
- var mathFunOpArr = arrayOf("SQRT", "DISTANCE", "POWER", "MAX", "MIN", "AVERAGE", "COUNT", "ROUND", "NUMBER", "DECIMAL", "SUM", "LIST","ABS")
- var dateTimeOpArr = arrayOf("NOW", "TODAY", "TIMENOW", "DATETIME", "TIME", "DATE", "WEEKNUM", "WEEKDAY", "YEAR", "MONTH", "SECOND", "MINUTE", "HOUR",
- "TIMENUMBER", "TIMEDURATION", "DATEDURATION", "DATENUMBER", "DATETIMENUMBER", "DATETIMEDURATION", "DURATIONNUMBER", "DURATIONDURATION")
- var functionArr = arrayOf(
- "UPPER", "LOWER", "CONCATENATE", "SQRT",
- "DISTANCE", "POWER", "ABS", "MAX", "MIN", "AVERAGE", "COUNT", "ROUND",
- "STDEVP", "FLOOR", "CEILING", "NUMBER", "DECIMAL", "SUM", "LIST", "LEFT"
- )
- fun getStackTokenArr(str: String): ArrayList<String> {
- var stackArr: ArrayList<String> = arrayListOf<String>()
- var getVal: String = ""
- var breakExpressions = "(,)"
- str.forEachIndexed { index, charData ->
- if (charData != null && breakExpressions.contains(charData)) {
- stackArr.add(getVal)
- stackArr.add(charData.toString())
- getVal = ""
- } else {
- getVal = "${getVal}${charData}"
- }
- }
- stackArr.add(getVal)
- return stackArr
- }
- //Function To Get Type Of Variables in Operator Operand Stack
- fun checkVariableType(position: Int, fieldsList: ArrayList<FieldItem>?): VARIABLE_TYPE {
- var checkVar = stackTokenArr?.get(position)
- if (functionArr.any { it == checkVar }) {
- return VARIABLE_TYPE.FUNCTION
- } else if (operatorArr.any { it == checkVar }) {
- return VARIABLE_TYPE.OPERATOR
- } else if ((checkVar ?: "").contains("[") && (checkVar ?: "").contains("]")) {
- fieldsList?.forEachIndexed { index, fieldItem ->
- var regex = fieldItem.fieldTitle?.toRegex()
- if (regex?.containsMatchIn((checkVar ?: "")) ?: false) {
- stackTokenArr?.get(position)?.replace(checkVar ?: "", fieldItem.fieldValue
- ?: "")
- }
- }
- return VARIABLE_TYPE.COLOUM_VALUE
- } else if (checkVar.equals("(")) {
- return VARIABLE_TYPE.START_BRACKET
- } else if (checkVar.equals(")")) {
- return VARIABLE_TYPE.POP_TO_EVALUATE
- } else if ((checkVar ?: "").isDigitsOnly()) {
- return VARIABLE_TYPE.CONSTANT
- }
- return VARIABLE_TYPE.IGNORE
- }
- fun checkVariableType(position: Int): VARIABLE_TYPE {
- var checkVar = stackTokenArr?.get(position)
- if (functionArr.any { it == checkVar }) {
- return VARIABLE_TYPE.FUNCTION
- } else if (operatorArr.any { it == checkVar }) {
- return VARIABLE_TYPE.OPERATOR
- } else if ((checkVar ?: "").contains("[") && (checkVar ?: "").contains("]")) {
- return VARIABLE_TYPE.COLOUM_VALUE
- } else if (checkVar.equals("(")) {
- return VARIABLE_TYPE.START_BRACKET
- } else if (checkVar.equals(")")) {
- return VARIABLE_TYPE.POP_TO_EVALUATE
- } /*else if ((checkVar?:"").isDigitsOnly()) {
- return VARIABLE_TYPE.CONSTANT
- }*/
- return VARIABLE_TYPE.IGNORE
- }
- /**
- * replace column name with column value
- */
- fun checkReplace(stackToken: String?, fieldsList: ArrayList<FieldItem>?): SparseArray<FieldItem> {
- var isColumnContains = SparseArray<FieldItem>()
- fieldsList?.forEachIndexed { index, fieldItem ->
- var regex = fieldItem.fieldTitle?.toRegex()
- if (regex?.containsMatchIn((stackToken ?: "")) ?: false) {
- isColumnContains.put(index, fieldItem)
- }
- }
- return isColumnContains
- }
- /**
- * handle to manage all kind of formula
- */
- @JvmStatic
- fun manageFormulaStack(formula: String, fieldsList: ArrayList<FieldItem>?): String {
- stackTokenArr = getStackTokenArr(formula)
- var ops = Stack<String>()
- var vals = Stack<String>()
- stackTokenArr?.forEachIndexed { index, strData ->
- var args = checkVariableType(index)
- if (args.equals(VARIABLE_TYPE.COLOUM_VALUE)) {
- var data = checkReplace(strData, fieldsList)
- if (data.size() > 0) {
- stackTokenArr?.set(index, data.valueAt(0).fieldValue ?: "")
- println("replacedData:${stackTokenArr?.get(index)}")
- }
- }
- if (args.equals(VARIABLE_TYPE.IGNORE))
- else if (args.equals(VARIABLE_TYPE.START_BRACKET))
- else if (args.equals(VARIABLE_TYPE.FUNCTION)) {
- ops.push(strData)
- } else if (args.equals(VARIABLE_TYPE.POP_TO_EVALUATE)) {
- var op = ops.pop()
- if (txtFunctionArr.any { it == op }) {
- var opData = ArrayList<String>()
- for (index in 0 until vals.size) {
- opData.add(vals.pop())
- }
- var result = handleTxtFunArr(op,opData)
- vals.push("${result}")
- }
- else if (mathFunOpArr.any { it == op }) {
- var opData = ArrayList<String>()
- for (index in 0 until vals.size) {
- opData.add(vals.pop())
- }
- var result = handleMathFunOpArr(op,opData)
- vals.push("${result}")
- }/*("DISTANCE", "NUMBER", "DECIMAL","LIST")*/
- else if (operatorArr.any { it == op }) {
- var opData = ArrayList<String>()
- for (index in 0 until vals.size) {
- opData.add(vals.pop())
- }
- var result = handleOperatorArr(op,opData)
- vals.push("${result}")
- }
- else if (dateTimeOpArr.any { it == op }) {
- var opData = ArrayList<String>()
- for (index in 0 until vals.size) {
- opData.add(vals.pop())
- }
- var result = handleDateTimeFunArr(op,opData)
- vals.push("${result}")
- }
- } else {
- vals.push(stackTokenArr?.get(index))
- }
- }
- var resultPoped = ""
- if(vals.size>0){
- resultPoped = vals.pop()
- println("Final print values:${resultPoped}")
- }
- return "${resultPoped}"
- }
- /**
- * handle to perform text formula
- */
- fun handleTxtFunArr(op:String,opData:ArrayList<String>):String{
- var finalResult = ""
- when (op) {
- "UPPER" -> {
- try {
- var finalData = opData?.get(0)?.toUpperCase()?:""
- finalResult = "${finalData}"
- } catch (e: Exception) {
- }
- }
- "LOWER" -> {
- try {
- var finalData = opData?.get(0)?.toLowerCase()?:""
- finalResult = "${finalData}"
- } catch (e: Exception) {
- }
- }
- "LEN" -> {
- try {
- var finalData = opData.get(0).length?:0
- finalResult = "${finalData}"
- } catch (e: Exception) {
- }
- }
- "LEFT" -> {
- try {
- var strData = opData?.get(0)?:""
- var range = opData.get(1).toInt()?:0
- var finalData = ASStringUtils.findLeftString(strData,range )
- finalResult = "${finalData}"
- } catch (e: Exception) {
- }
- }
- "RIGHT" -> {
- try {
- var strData = opData?.get(0)?:""
- var range = opData.get(1).toInt()?:0
- var finalData = ASStringUtils.findRightString(strData,range )
- finalResult = "${finalData}"
- } catch (e: Exception) {
- }
- }
- "TRIM" -> {
- var finalData = opData.get(0).trim()?:""
- finalResult = "${finalData}"
- }
- "FIND" -> {
- try {
- var searchContain = opData?.get(0)?:""
- var searchTxt = opData?.get(1)?:""
- finalResult = "${searchContain.split(searchTxt.toRegex(),1)?.get(0)?.length?:0}"
- } catch (e: Exception) {
- }
- }
- "CONCATENATE" -> {
- try {
- var finalData:StringBuffer = StringBuffer()
- for (index in 0 until opData.size) {
- finalData = finalData.append(Regex("[,]").replace(opData.get(index), ""))
- }
- finalResult = "${finalData}"
- } catch (e: Exception) {
- }
- }
- }
- return finalResult
- }
- /**
- * handle to perform operator{like +,-,*,/,%} formula
- */
- fun handleOperatorArr(op:String,opData:ArrayList<String>):String{
- var value = opData.get(0).toDouble()?:0.0
- var value1 = opData.get(1).toDouble()?:0.0
- when (op) {
- "/" -> {
- value /= value1
- }
- "*" -> {
- value *= value1
- }
- "+" -> {
- value += value1
- }
- "-" -> {
- value -= value1
- }
- "%" -> {
- value %= value1
- }
- }
- return "${value}"
- }
- /**
- * handle to perform math like{MAX,MIN,AVG,SUM,LIST,ROUND,COUNT.. etc} formula
- */
- fun handleMathFunOpArr(op:String,opData:ArrayList<String>):String{
- var finalResult = ""
- when (op) {
- "MAX" -> {
- var maxData: DoubleArray = DoubleArray(opData.size)
- for (index in 0 until opData.size) {
- maxData[index] = opData.get(index).toDouble()?:0.0
- }
- var finalMaxData = ASMath.max(maxData)?:0.0
- finalResult = "${finalMaxData}"
- }
- "MIN" -> {
- var minData: DoubleArray = DoubleArray(opData.size)
- for (index in 0 until opData.size) {
- minData[index] = opData.get(index).toDouble()?:0.0
- }
- var finalMinData = ASMath.min(minData)?:0.0
- finalResult = "${finalMinData}"
- }
- "AVERAGE" -> {
- var avgData: DoubleArray = DoubleArray(opData.size)
- for (index in 0 until opData.size) {
- avgData[index] = opData.get(index).toDouble()?:0.0
- }
- var finalAvgData = ASMath.average(avgData)?:0.0
- finalResult = "${finalAvgData}"
- }
- "SUM" -> {
- var sumData: DoubleArray = DoubleArray(opData.size)
- for (index in 0 until opData.size) {
- sumData[index] = opData.get(index).toDouble()?:0.0
- }
- var finalSumData = ASMath.sum(sumData)?:0.0
- finalResult = "${finalSumData}"
- }
- "LIST" -> {
- /* var listData:DoubleArray= DoubleArray(vals.size)
- for (index in 0 until vals.size) {
- listData[index] = vals.pop().toDouble()
- }
- vals.push("${listData}")*/
- }
- "ROUND" -> {
- try {
- var p = opData.get(0).toInt()?:0
- var n = opData.get(0).toDouble()?:0.0
- var value = ASMath.round(n, p)?:0.0
- finalResult = "${value}"
- } catch (e: Exception) {
- }
- }
- "COUNT" -> {
- finalResult = "${opData.size ?: 0}"
- }
- "SQRT" -> {
- finalResult = "${Math.sqrt(opData.get(0).toDouble()?: 0.0)}"
- }
- "POWER" -> {
- var value = opData.get(0)?.toDouble()?:0.0
- var powerValue = opData.get(1)?.toDouble()?:0.0
- finalResult = "${Math.pow(value,powerValue)}"
- }
- "ABS" -> {
- var value = opData.get(0)?.toDouble()?:0.0
- finalResult = "${Math.abs(value)}"
- }
- }
- return finalResult
- }
- /**
- * handle to perform date,time and datetime formula
- */
- fun handleDateTimeFunArr(op:String,opData:ArrayList<String>):String{
- var finalResult = ""
- when (op) {
- "NOW" -> {
- }
- "TODAY" -> {
- }
- "TIMENOW" -> {
- }
- "DATETIME" -> {
- }
- "TIME" -> {
- }
- "DATE" -> {
- }
- "WEEKNUM" -> {
- }
- "WEEKDAY" -> {
- }
- "YEAR" -> {
- }
- "MONTH" -> {
- }
- "SECOND" -> {
- }
- "MINUTE" -> {
- }
- "HOUR" -> {
- }
- "TIMENUMBER" -> {
- }
- "TIMEDURATION" -> {
- }
- "DATEDURATION" -> {
- }
- "DATENUMBER" -> {
- }
- "DATETIMENUMBER" -> {
- }
- "DATETIMEDURATION" -> {
- }
- "DURATIONNUMBER" -> {
- }
- "DURATIONDURATION" -> {
- }
- }
- return finalResult
- }
- }
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement