我寫了一套數學圖形可視化的工具,能夠將數學表達式以圖形的形式顯示出來.html
軟件下載地址:http://files.cnblogs.com/WhyEngine/WhyMathGraph.zip數組
源碼下載地址: http://pan.baidu.com/s/1jG9QKq6less
QQ交流羣: 367752815ide
在這套軟件中,我首先制訂了一套腳本語言.語法很簡單,用於描述數學參數方程,以作爲軟件的輸入數據.函數
先看下面的腳本程序工具
vertices = 1200 x = from (-4*PI) to (4*PI) y = sin(x)
vertices = D1:360 D2:100 u = from 0 to 1 D1 v = from -1 to 1 D2 s = 10 x = s*u y = s*v*sin(u*2*PI) u = u*5 v = v*5
(1)頂點數目設置spa
在計算機圖形學中曲線是由頂點組成的code
'vertices = 1200' 表示頂點數目,意味着整個曲線上有1200個頂點.
該軟件不只支持曲線還支持曲面,若是是數學曲面圖形腳本的話,其頂點輸入應該是一個二維的數據.
二維數據用於生成生成曲面圖形,其定義以下:htm
vertices = dimension1:80 dimension2:160 或blog
vertices = D1:80 D2:160
這裏表示第一個維度的輸入爲80,第二個維度的輸入爲160,總體輸入的頂點數目爲80*160.而生成的曲面三角形數目爲79*159*2個.
(2)常數值
腳本程序中PI爲定義的常數值,就是圓周率,目前軟件中有5個常數值
PI 3.1415927
E 2.7182818
GOLD 0.6180034
SQRT2 1.4142136
SQRT3 1.7320508
常量名一般爲大寫字母,如 (PI + E) 或 sin(PI*0.5)
(3)數值解析
對整數的解析支持2,8,10,16四種進制
0X開頭爲16進制, XABCDEF大小寫均可以, 如0xffff
0Y開頭爲2進制, Y大小寫均可以, 如0y10101010000
0開頭爲8進制, 如07523, 注意出現了"08"之類的會解析失敗
默認爲10進制
對浮點數的解析支持兩種方式
(a)形如」0.12」的格式,不能省略前面的0,後面也不能加f
(b)科學表達格式.形如1.2e2
系統中使用a-z的26個英文小寫字母表示變量,變量可以存儲單個實數,或一個實數數組.若是爲實數數據,則其數組大小爲以前設置的頂點數目(見1).
設置爲單個實數
a = 3.1415 // 將a賦值爲3.1415
a = PI // 將a賦值爲常量PI
a = 0y10101010000 //2進制
a = 07523 //8進制
一維數組的設置
a = from 0 to 100 // a爲一個實數數組,數組大小爲vertices的設置,數值爲線性插值求得.獲得一個等差數組.
二維數據的設置
a = from 0 to (2*PI) dimension1
b = from (-PI*0.5) to (PI*0.5) dimension2
或者
a = from 0 to (2*PI) D1
b = from (-PI*0.5) to (PI*0.5) D2
這裏的D1,D2表示這兩個數組是第一維度的數據仍是第二個維度的數據.
若是以前設置的vertices = D1:80 D2:160,那麼這裏a,b所生成的數組大小爲80*160
對輸出變量的使用:
軟件中將變量x,y,z組成3D頂點位置座標
r,g,b將組成頂點顏色.其值範圍在0-1.0之間.若是沒有設置r,g,b,將使用默認方式生成頂點色.
u,v爲頂點的紋理座標,若是沒有設置u,v,將使用x,z生成頂點的紋理座標.
(5)運算符
運算符這一塊比較多,用戶最好看下
」. \MathGraph\Project\MathExpression\operator.cpp」文件中的代碼.
以及文件夾」 \MathScript\函數面\」裏面的腳本文件.
標準單目運算符
+,-
如:a = -b
標準雙目運算符
+,-,*,/,%,^ <,>,=,&,|
如:c = a * b 若是a,b都爲單個實數則運算結果c也是單個實數,不然c爲實數數組.
a^b 等同於pow(a, b)
&|爲邏輯運算符,規定當變量-1<a<1時爲false,不然爲true
函數單目運算符 形如sin(a)
positive,negative,abs,floor,ceil,sign,sqrt,exp,log,log2,log10,sin,cos,tan,asin,acos,atan,rand等
相關代碼以下:
const Operator singleOperators[SINGLE_OPERATORS_COUNT] =
{
{"positive", 0, OT_SINGLE, yf_positive, 0, 0, 0, 0, 0}, {"negative", 0, OT_SINGLE, yf_negative, 0, 0, 0, 0, 0}, {"abs", 0, OT_SINGLE, yf_abs, 0, 0, 0, 0, 0}, {"floor", 0, OT_SINGLE, yf_floor, 0, 0, 0, 0, 0}, {"ceil", 0, OT_SINGLE, yf_ceil, 0, 0, 0, 0, 0}, {"sign", 0, OT_SINGLE, yf_sign, 0, 0, 0, 0, 0}, {"rand", 0, OT_SINGLE, yf_rand, 0, 0, 0, 0, 0}, {"rand_int", 0, OT_SINGLE, yf_rand_int, 0, 0, 0, 0, 0}, {"round", 0, OT_SINGLE, yf_round, 0, 0, 0, 0, 0}, {"sqrt", 0, OT_SINGLE, yf_sqrt, 0, 0, 0, 0, 0}, {"exp", 0, OT_SINGLE, yf_exp, 0, 0, 0, 0, 0}, {"log", 0, OT_SINGLE, yf_log, 0, 0, 0, 0, 0}, {"ln", 0, OT_SINGLE, yf_log, 0, 0, 0, 0, 0}, // log == ln {"log10", 0, OT_SINGLE, yf_log10, 0, 0, 0, 0, 0}, {"lg", 0, OT_SINGLE, yf_log10, 0, 0, 0, 0, 0}, // log10 = lg {"log2", 0, OT_SINGLE, yf_log2, 0, 0, 0, 0, 0}, {"sin", 0, OT_SINGLE, yf_sin, 0, 0, 0, 0, 0}, {"cos", 0, OT_SINGLE, yf_cos, 0, 0, 0, 0, 0}, {"tan", 0, OT_SINGLE, yf_tan, 0, 0, 0, 0, 0}, {"cot", 0, OT_SINGLE, yf_cot, 0, 0, 0, 0, 0}, {"ctg", 0, OT_SINGLE, yf_cot, 0, 0, 0, 0, 0}, {"asin", 0, OT_SINGLE, yf_asin, 0, 0, 0, 0, 0}, {"acos", 0, OT_SINGLE, yf_acos, 0, 0, 0, 0, 0}, {"atan", 0, OT_SINGLE, yf_atan, 0, 0, 0, 0, 0}, {"acot", 0, OT_SINGLE, yf_acot, 0, 0, 0, 0, 0}, {"arcsin", 0, OT_SINGLE, yf_asin, 0, 0, 0, 0, 0}, {"arccos", 0, OT_SINGLE, yf_acos, 0, 0, 0, 0, 0}, {"arctan", 0, OT_SINGLE, yf_atan, 0, 0, 0, 0, 0}, {"arccot", 0, OT_SINGLE, yf_acot, 0, 0, 0, 0, 0}, {"sinh", 0, OT_SINGLE, yf_sinh, 0, 0, 0, 0, 0}, // 雙曲正弦函數 {"cosh", 0, OT_SINGLE, yf_cosh, 0, 0, 0, 0, 0}, // 雙曲餘弦函數 {"tanh", 0, OT_SINGLE, yf_tanh, 0, 0, 0, 0, 0}, // 雙曲正切函數 {"coth", 0, OT_SINGLE, yf_coth, 0, 0, 0, 0, 0}, // 雙曲餘切函數 {"sh", 0, OT_SINGLE, yf_sh, 0, 0, 0, 0, 0}, // 雙曲正弦函數 {"ch", 0, OT_SINGLE, yf_ch, 0, 0, 0, 0, 0}, // 雙曲餘弦函數 {"th", 0, OT_SINGLE, yf_th, 0, 0, 0, 0, 0}, // 雙曲正切函數 {"cth", 0, OT_SINGLE, yf_cth, 0, 0, 0, 0, 0}, // 雙曲餘切函數 {"sec", 0, OT_SINGLE, yf_sec, 0, 0, 0, 0, 0}, // 正割函數 {"csc", 0, OT_SINGLE, yf_csc, 0, 0, 0, 0, 0}, // 餘割函數 {"sech", 0, OT_SINGLE, yf_sech, 0, 0, 0, 0, 0}, // 雙曲正割(等同於sch) {"sch", 0, OT_SINGLE, yf_sech, 0, 0, 0, 0, 0}, // 雙曲正割 {"csch", 0, OT_SINGLE, yf_csch, 0, 0, 0, 0, 0}, // 雙曲餘割(等同於xh) {"xh", 0, OT_SINGLE, yf_csch, 0, 0, 0, 0, 0}, // 雙曲餘割 };
函數雙目運算符 形如pow(a, b)
add,sub,multiply,divide,max,min,mod,pow,atan2,rand2,等
const Operator twinOperators[TWIN_OPERATORS_COUNT] = { {"add", 0, OT_TWIN, 0, yf_add, 0, 0, 0, 0}, {"sub", 0, OT_TWIN, 0, yf_sub, 0, 0, 0, 0}, {"multiply", 0, OT_TWIN, 0, yf_multiply, 0, 0, 0, 0}, {"divide", 0, OT_TWIN, 0, yf_divide, 0, 0, 0, 0}, {"max", 0, OT_TWIN, 0, yf_max, 0, 0, 0, 0}, {"min", 0, OT_TWIN, 0, yf_min, 0, 0, 0, 0}, {"mod", 0, OT_TWIN, 0, yf_mod, 0, 0, 0, 0}, {"pow", 0, OT_TWIN, 0, yf_pow, 0, 0, 0, 0}, {"log_ax", 0, OT_TWIN, 0, yf_log_ax, 0, 0, 0, 0}, {"pow_sign", 0, OT_TWIN, 0, yf_pow_sign, 0, 0, 0, 0}, {"correction_gamma",0, OT_TWIN, 0, yf_correction_gamma, 0, 0, 0, 0}, {"correction_pow", 0, OT_TWIN, 0, yf_correction_pow, 0, 0, 0, 0}, {"correction_sin", 0, OT_TWIN, 0, yf_correction_sin, 0, 0, 0, 0}, {"atan2", 0, OT_TWIN, 0, yf_atan2, 0, 0, 0, 0}, {"rand2", 0, OT_TWIN, 0, yf_rand2, 0, 0, 0, 0}, {"rand_int2", 0, OT_TWIN, 0, yf_rand_int2, 0, 0, 0, 0}, {"and", 0, OT_TWIN, 0, yf_and, 0, 0, 0, 0}, {"or", 0, OT_TWIN, 0, yf_or, 0, 0, 0, 0}, {"xor", 0, OT_TWIN, 0, yf_xor, 0, 0, 0, 0}, {"greater", 0, OT_TWIN, 0, yf_greater, 0, 0, 0, 0}, {"greater_equal", 0, OT_TWIN, 0, yf_greater_equal,0, 0, 0, 0}, {"less", 0, OT_TWIN, 0, yf_less, 0, 0, 0, 0}, {"less_equal", 0, OT_TWIN, 0, yf_less_equal, 0, 0, 0, 0}, {"equal", 0, OT_TWIN, 0, yf_equal, 0, 0, 0, 0}, };
函數三目運算符 形如lerp(a, b, r)
lerp,clamp,gray,add3,min3,max3,average3
const Operator threeOperators[THREE_OPERATORS_COUNT] = { {"lerp", 0, OT_THREE, 0, 0, yf_lerp, 0, 0, 0}, {"clamp", 0, OT_THREE, 0, 0, yf_clamp, 0, 0, 0}, {"limit", 0, OT_THREE, 0, 0, yf_limit, 0, 0, 0}, {"in_range", 0, OT_THREE, 0, 0, yf_in_range, 0, 0, 0}, {"gray", 0, OT_THREE, 0, 0, yf_gray, 0, 0, 0}, {"add3", 0, OT_THREE, 0, 0, yf_add3, 0, 0, 0}, {"min3", 0, OT_THREE, 0, 0, yf_min3, 0, 0, 0}, {"max3", 0, OT_THREE, 0, 0, yf_max3, 0, 0, 0}, {"average3", 0, OT_THREE, 0, 0, yf_average3, 0, 0, 0}, {"if", 0, OT_THREE, 0, 0, yf_if, 0, 0, 0}, };
比較特殊的是if函數,能夠參考這個例子:
vertices = 12000 x = from (-4) to (4) t = mod(x, 2) y = if(t, sin(x*PI), tan(x*PI))
經過if函數,生成一個sin曲線與tan曲線交錯的曲線
函數四目運算符 形如average4(a, b, c, d)
add4,min4,max4,average4
const Operator fourOperators[FOUR_OPERATORS_COUNT] = { {"add4", 0, OT_FOUR, 0, 0, 0, yf_add4, 0, 0}, {"min4", 0, OT_FOUR, 0, 0, 0, yf_min4, 0, 0}, {"max4", 0, OT_FOUR, 0, 0, 0, yf_max4, 0, 0}, {"average4", 0, OT_FOUR, 0, 0, 0, yf_average4, 0, 0}, };
函數數組運算符(輸入實數數組,輸出一個浮點數,如求最大值,最小值,數組加和等)
add_array,min_array,max_array,ave_array
const Operator valueNodeOperators[VALUENODE_TO_FLOAT_OPERATORS_COUNT] = { {"array_add", 0, OT_VALUENODE_TO_FLOAT, 0, 0, 0, 0, yf_add_array, 0}, {"array_min", 0, OT_VALUENODE_TO_FLOAT, 0, 0, 0, 0, yf_min_array, 0}, {"array_max", 0, OT_VALUENODE_TO_FLOAT, 0, 0, 0, 0, yf_max_array, 0}, {"array_ave", 0, OT_VALUENODE_TO_FLOAT, 0, 0, 0, 0, yf_average_array, 0}, };
函數數組運算符(輸入實數數組,輸出也是實數數組,如求數組左移,數組右移,前向累加等)
array_move_right,array_move_left,array_cumulate
const Operator valueNode2Operators[VALUENODE_CONVERT_OPERATORS_COUNT] = { {"array_move_right",0, OT_VALUENODE_TO_FLOAT, 0, 0, 0, 0, 0, yf_array_move_right}, {"array_move_left", 0, OT_VALUENODE_TO_FLOAT, 0, 0, 0, 0, 0, yf_array_move_left}, {"array_cumulate", 0, OT_VALUENODE_TO_FLOAT, 0, 0, 0, 0, 0, yf_array_cumulate}, };
(6)運算符嵌套
支持{}, [], ()這三類括號標誌符,括號必需成對出現.支持最大32級括號的嵌套.如:
(2+(-2+(5.0*(9 + ((1+2)*3))/3) + 2))
-{exp[5*sqrt(1 -abs[sin{rand(100)}]) + 6]}
========================================================
(1)單目運算函數,形如a = log(b)
"positive", // 取正,基本上沒什麼用,至關於(+a)
"negative", // 取負
"abs", // 求絕對值
"floor", // 整數位
"ceil", // 整數位+1
"sign", // 返回-1.0或1.0
"sgn", // 返回-1.0或0.0或1.0
"is_zero", // 返回0.0或1.0
"rand", // 返回一個隨機的浮點數
"rand_int", // 返回一個隨機整數
"round", // 四捨五入
"reciprocal", // 倒數
"sqrt", // 開根號
"exp", //
"log", // 求對數
"ln", // log == ln
"log10",
"lg", // log10 = lg
"log2",
"sin", // 正弦函數
"cos", // 餘弦函數
"asin", // 反正弦函數
"acos", // 反餘弦函數
"arcsin", // 反正弦函數
"arccos", // 反餘弦函數
"tan", // 正切函數
"cot", // 餘切函數
"ctg", // 餘切函數
"atan", // 反正切函數
"acot", // 反餘切函數
"actg", // 反餘切函數
"arctan", // 反正切函數
"arccot", // 反餘切函數
"arcctg", // 反餘切函數
"sec", // 正割函數
"csc", // 餘割函數
"asec", // 反正割函數
"acsc", // 反餘割函數
"arcsec", // 反正割函數
"arccsc", // 反餘割函數
"sinh", // 雙曲正弦函數
"cosh", // 雙曲餘弦函數
"tanh", // 雙曲正切函數
"coth", // 雙曲餘切函數
"sh", // 雙曲正弦函數
"ch", // 雙曲餘弦函數
"th", // 雙曲正切函數
"cth", // 雙曲餘切函數
"sech", // 雙曲正割(等同於sch)
"sch", // 雙曲正割
"csch", // 雙曲餘割(等同於xh)
"xh", // 雙曲餘割
"factorial", // 階乘
"erf", // 偏差函數
"float_to_color", // 將浮點數轉化爲0-255的顏色數
(2)雙目運算函數,形如a = add(b, c)
"add", 相加
"sub", 相減
"multiply", 相乘
"divide", 相除
"max", // 返回兩數較大的一個
"min", // 返回兩數較小的一個
"mod", // 求餘
"pow", // 求冪
"log_ax", // 對數
"pow_sign", // 用於對負數的求冪,至關於pow(abs(a), b)
"correction_gamma",// gamma校訂函數
"correction_pow", // pow校訂函數
"correction_sin", // sin校訂函數
"atan2", // 正切
"rand2", // 返回兩數之間的一個隨機浮點數
"rand_int2", // 返回兩數之間的一個隨機整數
"and_bool" // 與,返回0或1.0
"or_bool", // 或,返回0或1.0
"xor_bool" // 異或,返回0或1.0
"and_byte" // 與,返回0到255.0的一個數
"or_byte", // 或,返回0到255.0的一個數
"xor_byte" // 異或,返回0到255.0的一個數
"and_word" // 與,返回0到65535.0的一個數
"or_word", // 或,返回0到65535.0的一個數
"xor_word" // 異或,返回0到65535.0的一個數
"greater", // 返回0或1.0
"greater_equal", // 返回0或1.0
"less", // 返回0或1.0
"less_equal", // 返回0或1.0
"equal", // 返回0或1.0
(3)三目運算符函數 形如lerp(a, b, r)
"lerp", // 線性插值
"clamp", // 限定數值的範圍
"limit", // 限定數值的範圍,與clamp同樣
"in_range", // 數值是否範圍內,返回0或1.0
"gray", // 顏色的灰度化
"add3", // 相加
"min3", // 三個之中取最小
"max3", // 三個之中取最大
"average3", // 三數平均值
"if", // 若是第一個數不爲0則取第二個數,不然取第三個數
"if_else", // 與if等價
(4)函數四目運算符 形如average4(a, b, c, d)
"add4", // 相加
"min4", // 四個之中取最小
"max4", // 四個之中取最大
"average4", // 四數平均值
(5)函數數組運算符(輸入實數數組,輸出一個浮點數,如求最大值,最小值,數組加和等)
"array_add", // 相加
"array_min", // 數組之中取最小
"array_max", // 數組之中取最大
"array_ave", // 數組平均值
(6)函數數組運算符(輸入實數數組,輸出也是實數數組,如求數組左移,數組右移,前向累加等)
"array_move_right",// 數組右移
"array_move_left", // 數組左移
"array_cumulate", // 數組累加
"array_difference",// 數組差,b[n] = a[n + params] - a[n]
(7)函數數組運算符(輸入兩個浮點數,輸出實數數組)
"array_lerp", // 將數組中的數值變爲等差數列
"array_rand", // 將數組中的數值變爲隨機浮點數
"array_rand_int", // 將數組中的數值變爲隨機整數
"array_set_all_values",// 將數組設置爲統一值
(8)函數數組運算符(輸入實數數組和一個浮點數,輸出一個浮點數)"array_get_value" // 獲取數組的某一個值