/// <summary> /// Utility function which takes a specialized multivector and returns an array of its variable /// RefGA.BasisBlades. I.e., extracts 'smv.NonConstBasisBlade()' /// </summary> /// <param name="smv">Specialized multivector.</param> /// <returns>Array of non-constant basis blades of 'smv'.</returns> public static RefGA.BasisBlade[] GetNonConstBladeList(G25.SMV smv) { RefGA.BasisBlade[] BL = new RefGA.BasisBlade[smv.NbNonConstBasisBlade]; for (int i = 0; i < smv.NbNonConstBasisBlade; i++) BL[i] = smv.NonConstBasisBlade(i); return BL; }
/// <summary> /// Returns the name of the constant as first argument to functions which have coordinate arguments. /// </summary> /// <param name="S"></param> /// <param name="smv"></param> public static string GetCoordinateOrderConstant(Specification S, G25.SMV smv) { StringBuilder SB = new StringBuilder("coord"); string wedgeSymbol = ""; // no symbol for wedge for (int i = 0; i < smv.NbNonConstBasisBlade; i++) { SB.Append("_"); SB.Append(smv.NonConstBasisBlade(i).ToLangString(S.m_basisVectorNames, wedgeSymbol)); } return SB.ToString(); }
/// <summary> /// Writes getters and setters for the SMV coordinates.. /// </summary> /// <param name="SB">Where the code goes.</param> /// <param name="S">Used for basis vector names and output language.</param> /// <param name="cgd">Not used yet.</param> /// <param name="FT">Float point type of 'SMV'.</param> /// <param name="smv">The specialized multivector for which the struct should be written.</param> public static void WriteGetSetCoord(StringBuilder SB, Specification S, G25.CG.Shared.CGdata cgd, FloatType FT, G25.SMV smv) { // write variable coordinates for (int i = 0; i < smv.NbNonConstBasisBlade; i++) { string name = smv.NonConstBasisBlade(i).ToLangString(S.m_basisVectorNames); string accessName = GetCoordAccessString(S, smv, i); SB.AppendLine("\t/// Returns the " + smv.NonConstBasisBlade(i).ToString(S.m_basisVectorNames) + " coordinate."); SB.AppendLine("\tinline " + FT.type + " " + MainGenerator.GETTER_PREFIX + name + "() const { return " + accessName + ";}"); SB.AppendLine("\t/// Sets the " + smv.NonConstBasisBlade(i).ToString(S.m_basisVectorNames) + " coordinate."); SB.AppendLine("\tinline void " + MainGenerator.SETTER_PREFIX + name + "(" + FT.type + " " + name + ") { " + accessName + " = " + name + ";}"); } // write constant coordinates for (int i = 0; i < smv.NbConstBasisBlade; i++) { RefGA.BasisBlade B = smv.ConstBasisBlade(i); SB.AppendLine("\t/// Returns the " + B.ToString(S.m_basisVectorNames) + " coordinate."); SB.AppendLine("\tinline " + FT.type + " " + MainGenerator.GETTER_PREFIX + B.ToLangString(S.m_basisVectorNames) + "() const { return " + FT.DoubleToString(S, smv.ConstBasisBladeValue(i)) + ";}"); } // write a getter for the scalar which returns 0 if no scalar coordinate is present if (smv.GetElementIdx(RefGA.BasisBlade.ONE) < 0) { RefGA.BasisBlade B = RefGA.BasisBlade.ONE; SB.AppendLine("\t/// Returns the scalar coordinate (which is always 0)."); SB.AppendLine("\tinline " + FT.type + " " + MainGenerator.GETTER_PREFIX + B.ToLangString(S.m_basisVectorNames) + "() const { return " + FT.DoubleToString(S, 0.0) + ";}"); } // getter for the coordinates (stored in array) if ((S.m_coordStorage == COORD_STORAGE.ARRAY) && (smv.NbNonConstBasisBlade > 0)) { SB.AppendLine("\t/// Returns array of coordinates."); SB.AppendLine("\tinline const " + FT.type + " *getC(" + G25.CG.Shared.SmvUtil.COORDINATE_ORDER_ENUM + ") const { return m_c;}"); } }
/// <summary> /// Writes the SMV class comment 'SB'. /// </summary> /// <param name="SB">Where the code goes.</param> /// <param name="S">Used for basis vector names and output language.</param> /// <param name="cgd">Not used yet.</param> /// <param name="FT">Float point type of 'SMV'.</param> /// <param name="smv">The specialized multivector for which the struct should be written.</param> /// <param name="emitCoordIndices">Whether to emit constants for array indices to coordinates.</param> public static void WriteComment(StringBuilder SB, Specification S, G25.CG.Shared.CGdata cgd, FloatType FT, G25.SMV smv, bool emitCoordIndices) { SB.AppendLine("/**"); SB.AppendLine(" * This class can hold a specialized multivector of type " + FT.GetMangledName(S, smv.Name) + "."); SB.AppendLine(" * "); SB.AppendLine(" * The coordinates are stored in type " + FT.type + "."); SB.AppendLine(" * "); if (smv.NbNonConstBasisBlade > 0) { SB.AppendLine(" * The variable non-zero coordinates are:"); for (int i = 0; i < smv.NbNonConstBasisBlade; i++) { SB.AppendLine(" * - coordinate " + smv.NonConstBasisBlade(i).ToString(S.m_basisVectorNames) + " (array index: " + GetCoordIndexDefine(S, FT, smv, i) + " = " + i + ")"); } } else SB.AppendLine(" * The type is constant."); SB.AppendLine(" * "); if (smv.NbConstBasisBlade > 0) { SB.AppendLine(" * The constant non-zero coordinates are:"); for (int i = 0; i < smv.NbConstBasisBlade; i++) SB.AppendLine(" * - " + smv.ConstBasisBlade(i).ToString(S.m_basisVectorNames) + " = " + smv.ConstBasisBladeValue(i).ToString()); } else SB.AppendLine(" * The type has no constant coordinates."); SB.AppendLine(" * "); if ((smv.Comment != null) && (smv.Comment.Length > 0)) { SB.AppendLine(" * "); SB.AppendLine(" * " + smv.Comment); } SB.AppendLine(" */"); }
/// <summary> /// Writes the <c>defines</c> for indices of the smv struct to 'SB'. For example, <c>define VECTOR_E1 0</c>. /// </summary> /// <param name="SB">Where the code goes.</param> /// <param name="S">Used for basis vector names.</param> /// <param name="FT"></param> /// <param name="smv">The specialized multivector for which the coordinate indices should be written.</param> public static void WriteSMVcoordIndices(StringBuilder SB, Specification S, FloatType FT, G25.SMV smv) { string className = FT.GetMangledName(S, smv.Name); int nbTabs = 1; new G25.CG.Shared.Comment("Array indices of " + className + " coordinates.").Write(SB, S, nbTabs); string AccessModifier = Keywords.ConstAccessModifier(S); for (int i = 0; i < smv.NbNonConstBasisBlade; i++) { SB.AppendLine(); new G25.CG.Shared.Comment("index of coordinate for " + smv.NonConstBasisBlade(i).ToString(S.m_basisVectorNames) + " in " + className).Write(SB, S, nbTabs); SB.AppendLine("\tpublic " + AccessModifier + " int " + GetCoordIndexDefine(S, FT, smv, i) + " = " + i + ";"); } }
/// <summary> /// Writes a function to set an SMV class to specified coordinates, for all floating point types. /// </summary> /// <param name="S">Used for basis vector names and output language.</param> /// <param name="cgd">Intermediate data for code generation. Also contains plugins and cog.</param> public static void WriteSetCoords(Specification S, G25.CG.Shared.CGdata cgd, G25.FloatType FT, G25.SMV smv) { //if (smv.NbNonConstBasisBlade == 0) return; cgd.m_defSB.AppendLine(""); //string className = FT.GetMangledName(S, smv.Name); string funcName = GMV.GetSetFuncName(S); bool mustCast = false; System.Collections.ArrayList L = new System.Collections.ArrayList(); int NB_ARGS = 1 + smv.NbNonConstBasisBlade; string[] argTypename = new String[NB_ARGS]; string[] argName = new String[NB_ARGS]; argTypename[0] = G25.CG.Shared.SmvUtil.COORDINATE_ORDER_ENUM; argName[0] = "co"; for (int i = 0; i < smv.NbNonConstBasisBlade; i++) { RefGA.BasisBlade B = smv.NonConstBasisBlade(i); argTypename[i + 1] = FT.type; string coordStr = "_" + smv.GetCoordLangID(i, S, COORD_STORAGE.VARIABLES); argName[i + 1] = coordStr; L.Add(new RefGA.BasisBlade(B.bitmap, B.scale, coordStr)); } RefGA.Multivector mvValue = new RefGA.Multivector(L); G25.fgs F = new G25.fgs(funcName, funcName, "", argTypename, argName, new String[] { FT.type }, null, null, null); // null, null, null = metricName, comment, options F.InitArgumentPtrFromTypeNames(S); bool computeMultivectorValue = false; G25.CG.Shared.FuncArgInfo[] FAI = G25.CG.Shared.FuncArgInfo.GetAllFuncArgInfo(S, F, NB_ARGS, FT, null, computeMultivectorValue); string dstName = G25.CG.Shared.SmvUtil.THIS; bool dstPtr = false; bool staticFunc = false; G25.CG.Shared.Functions.WriteAssignmentFunction(S, cgd, S.m_inlineSet, staticFunc, "void", null, funcName, null, FAI, FT, mustCast, smv, dstName, dstPtr, mvValue); }
/// <summary> /// Writes a function to set an SMV struct to an array of specified coordinates, for all floating point types. /// </summary> /// <param name="S">Used for basis vector names and output language.</param> /// <param name="cgd">Intermediate data for code generation. Also contains plugins and cog.</param> public static void WriteSetArray(Specification S, G25.CG.Shared.CGdata cgd, G25.FloatType FT, G25.SMV smv) { //if (smv.NbNonConstBasisBlade == 0) return; cgd.m_defSB.AppendLine(""); //string className = FT.GetMangledName(S, smv.Name); string funcName = GMV.GetSetFuncName(S); bool mustCast = false; string[] argTypename = new string[2] { G25.CG.Shared.SmvUtil.COORDINATE_ORDER_ENUM, FT.type }; string[] argName = new string[2] { "co", "A" }; System.Collections.ArrayList L = new System.Collections.ArrayList(); for (int i = 0; i < smv.NbNonConstBasisBlade; i++) { RefGA.BasisBlade B = smv.NonConstBasisBlade(i); String coordStr = argName[1] + "[" + i + "]"; L.Add(new RefGA.BasisBlade(B.bitmap, B.scale, coordStr)); } RefGA.Multivector mvValue = new RefGA.Multivector(L); G25.fgs F = new G25.fgs(funcName, funcName, "", argTypename, argName, new string[] { FT.type }, null, null, null); // null, null, null = metricName, comment, options F.InitArgumentPtrFromTypeNames(S); F.SetArgumentArr(1, true); // second argument is an array bool computeMultivectorValue = false; int NB_ARGS = 2; // enum + one array of coordinates G25.CG.Shared.FuncArgInfo[] FAI = G25.CG.Shared.FuncArgInfo.GetAllFuncArgInfo(S, F, NB_ARGS, FT, null, computeMultivectorValue); string dstName = G25.CG.Shared.SmvUtil.THIS; bool dstPtr = false; bool staticFunc = false; G25.CG.Shared.Functions.WriteAssignmentFunction(S, cgd, S.m_inlineSet, staticFunc, "void", null, funcName, null, FAI, FT, mustCast, smv, dstName, dstPtr, mvValue); }
/// <summary> /// Writes the SMV class to 'SB' (including comments). /// </summary> /// <param name="SB">Where the code goes.</param> /// <param name="S">Used for basis vector names and output language.</param> /// <param name="cgd">Not used yet.</param> /// <param name="FT">Float point type of 'SMV'.</param> /// <param name="smv">The specialized multivector for which the struct should be written.</param> public static void WriteMemberVariables(StringBuilder SB, Specification S, G25.CG.Shared.CGdata cgd, FloatType FT, G25.SMV smv) { int nbTabs = 1; string accessModifier = Keywords.PackageProtectedAccessModifier(S); // individual coordinates or one array? if (S.m_coordStorage == COORD_STORAGE.VARIABLES) { for (int i = 0; i < smv.NbNonConstBasisBlade; i++) { string comment = "The " + smv.NonConstBasisBlade(i).ToString(S.m_basisVectorNames) + " coordinate."; new G25.CG.Shared.Comment(comment).Write(SB, S, nbTabs); SB.AppendLine("\t" + accessModifier + " " + FT.type + " m_" + smv.GetCoordLangID(i, S) + ";"); } } else { if (smv.NbNonConstBasisBlade > 0) { // emit: float c[3]; // e1, e2, e3 string comment = " The coordinates (stored in an array)."; new G25.CG.Shared.Comment(comment).Write(SB, S, nbTabs); SB.Append("\t" + accessModifier + " " + FT.type + "[] m_c = new " + FT.type + "[" + smv.NbNonConstBasisBlade + "]; // "); for (int i = 0; i < smv.NbNonConstBasisBlade; i++) { if (i > 0) SB.Append(", "); SB.Append(smv.NonConstBasisBlade(i).ToString(S.m_basisVectorNames)); } SB.AppendLine(""); } } }
/// <summary> /// Writes the SMV class to 'SB' (including comments). /// </summary> /// <param name="SB">Where the code goes.</param> /// <param name="S">Used for basis vector names and output language.</param> /// <param name="cgd">Not used yet.</param> /// <param name="FT">Float point type of 'SMV'.</param> /// <param name="smv">The specialized multivector for which the struct should be written.</param> public static void WriteMemberVariables(StringBuilder SB, Specification S, G25.CG.Shared.CGdata cgd, FloatType FT, G25.SMV smv) { SB.AppendLine("public:"); // individual coordinates or one array? if (S.m_coordStorage == COORD_STORAGE.VARIABLES) { for (int i = 0; i < smv.NbNonConstBasisBlade; i++) { SB.AppendLine("\t/// The " + smv.NonConstBasisBlade(i).ToString(S.m_basisVectorNames) + " coordinate."); SB.AppendLine("\t" + FT.type + " m_" + smv.GetCoordLangID(i, S) + ";"); } } else { if (smv.NbNonConstBasisBlade > 0) { // emit: float c[3]; // e1, e2, e3 SB.AppendLine("\t/// The coordinates (stored in an array)."); SB.Append("\t" + FT.type + " m_c[" + smv.NbNonConstBasisBlade + "]; // "); for (int i = 0; i < smv.NbNonConstBasisBlade; i++) { if (i > 0) SB.Append(", "); SB.Append(smv.NonConstBasisBlade(i).ToString(S.m_basisVectorNames)); } SB.AppendLine(""); } } }
/// <summary> /// Writes getters and setters for the SMV coordinates.. /// </summary> /// <param name="SB">Where the code goes.</param> /// <param name="S">Used for basis vector names and output language.</param> /// <param name="cgd">Not used yet.</param> /// <param name="FT">Float point type of 'SMV'.</param> /// <param name="smv">The specialized multivector for which the struct should be written.</param> public static void WriteGetSetCoord(StringBuilder SB, Specification S, G25.CG.Shared.CGdata cgd, FloatType FT, G25.SMV smv) { int nbTabs = 1; string className = FT.GetMangledName(S, smv.Name); // for variable coordinates: for (int i = 0; i < smv.NbNonConstBasisBlade; i++) { RefGA.BasisBlade B = smv.NonConstBasisBlade(i); string name = smv.NonConstBasisBlade(i).ToLangString(S.m_basisVectorNames); string accessName = G25.CG.Shared.SmvUtil.GetCoordAccessString(S, smv, i); // get string getComment = "Returns the " + B.ToString(S.m_basisVectorNames) + " coordinate."; new G25.CG.Shared.Comment(getComment).Write(SB, S, nbTabs); SB.AppendLine("\t" + Keywords.PublicAccessModifier(S) + " " + FT.type + " " + G25.CG.Shared.Main.GETTER_PREFIX + name + "() { return " + accessName + ";}"); // set string setComment = "Sets the " + B.ToString(S.m_basisVectorNames) + " coordinate."; new G25.CG.Shared.Comment(setComment).Write(SB, S, nbTabs); SB.AppendLine("\t" + Keywords.PublicAccessModifier(S) + " void " + G25.CG.Shared.Main.SETTER_PREFIX + name + "(" + FT.type + " " + name + ") { " + accessName + " = " + name + ";}"); } // for constant coordinates: for (int i = 0; i < smv.NbConstBasisBlade; i++) { RefGA.BasisBlade B = smv.ConstBasisBlade(i); // get string getComment = "Returns the " + B.ToString(S.m_basisVectorNames) + " coordinate."; new G25.CG.Shared.Comment(getComment).Write(SB, S, nbTabs); SB.AppendLine("\t" + Keywords.PublicAccessModifier(S) + " " + FT.type + " " + G25.CG.Shared.Main.GETTER_PREFIX + B.ToLangString(S.m_basisVectorNames) + "() { return " + FT.DoubleToString(S, smv.ConstBasisBladeValue(i)) + ";}"); } // write a getter for the scalar which returns 0 if no scalar coordinate is present if (smv.GetElementIdx(RefGA.BasisBlade.ONE) < 0) { RefGA.BasisBlade B = RefGA.BasisBlade.ONE; string getComment = "Returns the scalar coordinate (which is always 0)."; new G25.CG.Shared.Comment(getComment).Write(SB, S, nbTabs); SB.AppendLine("\t" + Keywords.PublicAccessModifier(S) + " " + FT.type + " " + G25.CG.Shared.Main.GETTER_PREFIX + B.ToLangString(S.m_basisVectorNames) + "() { return " + FT.DoubleToString(S, 0.0) + ";}"); } // getter for the coordinates (stored in array) if ((S.m_coordStorage == COORD_STORAGE.ARRAY) && (smv.NbNonConstBasisBlade > 0)) { string constantName = G25.CG.Shared.SmvUtil.GetCoordinateOrderConstant(S, smv); string COORD_ORDER = "coordOrder"; new G25.CG.Shared.Comment("Returns array of coordinates."). SetParamComment(COORD_ORDER, "pass the value '" + className + "." + constantName + "'"). Write(SB, S, nbTabs); SB.AppendLine("\t" + Keywords.PublicAccessModifier(S) + " " + FT.type + "[] c(" + G25.CG.Shared.SmvUtil.COORDINATE_ORDER_ENUM + " " + COORD_ORDER + ") { return m_c;}"); } }
public static string GenerateReturnCode(Specification S, G25.SMV smv, G25.FloatType FT, String[] valueStr, int nbTabs, bool writeZeros) { StringBuilder SB = new StringBuilder(); string smvName = FT.GetMangledName(S, smv.Name); string STATIC_MEMBER_ACCESS = (S.OutputCpp()) ? "::" : "."; SB.Append('\t', nbTabs); SB.Append("return "); if (S.OutputCSharpOrJava()) SB.Append("new "); SB.Append(smvName); SB.Append("("); if (valueStr.Length > 0) { SB.AppendLine(smvName + STATIC_MEMBER_ACCESS + SmvUtil.GetCoordinateOrderConstant(S, smv) + ","); } for (int i = 0; i < valueStr.Length; i++) { SB.Append('\t', nbTabs+2); SB.Append(valueStr[i]); if (i < (valueStr.Length - 1)) SB.Append(","); SB.AppendLine(" // " + smv.NonConstBasisBlade(i).ToLangString(S.m_basisVectorNames) ); } SB.Append('\t', nbTabs+1); SB.Append(");"); return SB.ToString(); }
/// <summary> /// Takes a specialized multivector specification (G25.SMV) and converts it into a symbolic multivector. /// The symbolic weights of the multivector are the coordinates of the SMV, labelled according to 'smvName'. /// /// An example is <c>A.c[0]*e1 + A.c[1]*e2 + A.c[2]*e3</c>. /// </summary> /// <param name="S">Specification of the algebra. Used for the access convention (. or ->) and for how to name the coordinates ([0] or e1, e2, e3).</param> /// <param name="smv">The specification of the specialized multivector.</param> /// <param name="smvName">Name the variable should have.</param> /// <param name="ptr">Is 'smvName' a pointer? This changes the way the variable is accessed.</param> /// <returns></returns> public static RefGA.Multivector SMVtoSymbolicMultivector(Specification S, G25.SMV smv, string smvName, bool ptr) { int idx = 0; // index into 'L' RefGA.BasisBlade[] L = new RefGA.BasisBlade[smv.NbConstBasisBlade + smv.NbNonConstBasisBlade]; string[] AL = CodeUtil.GetAccessStr(S, smv, smvName, ptr); // get non-const coords for (int i = 0; i < smv.NbNonConstBasisBlade; i++) { // get basis blade of coordinate RefGA.BasisBlade B = smv.NonConstBasisBlade(i); // merge L[idx++] = new RefGA.BasisBlade(B.bitmap, B.scale, AL[i]); } // get const coords for (int i = 0; i < smv.NbConstBasisBlade; i++) { // get value of coordinate double value = smv.ConstBasisBladeValue(i); // get basis blade of coordinate RefGA.BasisBlade B = smv.ConstBasisBlade(i); // merge L[idx++] = new RefGA.BasisBlade(B.bitmap, B.scale * value); } return new RefGA.Multivector(L); }
/// <summary> /// Writes the definition of an SMV struct to 'SB' (including comments). /// </summary> /// <param name="SB">Where the code goes.</param> /// <param name="S">Used for basis vector names and output language.</param> /// <param name="cgd">Not used yet.</param> /// <param name="FT">Float point type of 'SMV'.</param> /// <param name="smv">The specialized multivector for which the struct should be written.</param> public static void WriteSMVstruct(StringBuilder SB, Specification S, G25.CG.Shared.CGdata cgd, FloatType FT, G25.SMV smv) { SB.AppendLine(""); { // comments for type: SB.AppendLine("/**"); SB.AppendLine(" * This struct can hold a specialized multivector of type " + FT.GetMangledName(S, smv.Name) + "."); SB.AppendLine(" * "); SB.AppendLine(" * The coordinates are stored in type " + FT.type + "."); SB.AppendLine(" * "); if (smv.NbNonConstBasisBlade > 0) { SB.AppendLine(" * The variable non-zero coordinates are:"); for (int i = 0; i < smv.NbNonConstBasisBlade; i++) { SB.AppendLine(" * - coordinate " + smv.NonConstBasisBlade(i).ToString(S.m_basisVectorNames) + " (array index: " + GetCoordIndexDefine(S, smv, i) + " = " + i + ")"); } } else SB.AppendLine(" * The type is constant."); SB.AppendLine(" * "); if (smv.NbConstBasisBlade > 0) { SB.AppendLine(" * The constant non-zero coordinates are:"); for (int i = 0; i < smv.NbConstBasisBlade; i++) SB.AppendLine(" * - " + smv.ConstBasisBlade(i).ToString(S.m_basisVectorNames) + " = " + smv.ConstBasisBladeValue(i).ToString()); } else SB.AppendLine(" * The type has no constant coordinates."); SB.AppendLine(" * "); if ((smv.Comment != null) && (smv.Comment.Length > 0)) { SB.AppendLine(" * "); SB.AppendLine(" * " + smv.Comment); } SB.AppendLine(" */"); } // typedef SB.AppendLine("typedef struct "); SB.AppendLine("{"); // individual coordinates or one array? if (smv.NbNonConstBasisBlade > 0) { if (S.m_coordStorage == COORD_STORAGE.VARIABLES) { // emit float e1; float e2; float e3; for (int i = 0; i < smv.NbNonConstBasisBlade; i++) { SB.AppendLine("\t/** The " + smv.NonConstBasisBlade(i).ToString(S.m_basisVectorNames) + " coordinate. */"); SB.AppendLine("\t" + FT.type + " " + smv.GetCoordLangID(i, S) + ";"); //G25.CG.Shared.Util.BasisBladeToLangString(smv.NonConstBasisBlade(i), S.m_basisVectorNames) + ";"); } } else { // emit: float c[3]; // e1, e2, e3 SB.AppendLine("\t/** The coordinates (stored in an array). */"); SB.Append("\t" + FT.type + " c[" + smv.NbNonConstBasisBlade + "]; /* "); for (int i = 0; i < smv.NbNonConstBasisBlade; i++) { if (i > 0) SB.Append(", "); SB.Append(smv.NonConstBasisBlade(i).ToString(S.m_basisVectorNames)); } SB.AppendLine("*/"); } } else { SB.AppendLine("\t/** Filler, because C does not allow empty structs. */"); SB.AppendLine("\tint filler;"); } // emit: // no=1 for (int i = 0; i < smv.NbConstBasisBlade; i++) { SB.AppendLine("\t/* " + smv.ConstBasisBlade(i).ToString(S.m_basisVectorNames) + " = " + smv.ConstBasisBladeValue(i).ToString() + "*/"); } SB.AppendLine("} " + FT.GetMangledName(S, smv.Name) + ";"); }
/// <summary> /// Writes the <c>defines</c> for indices of the smv struct to 'SB'. For example, <c>define VECTOR_E1 0</c>. /// </summary> /// <param name="SB">Where the code goes.</param> /// <param name="S">Used for basis vector names.</param> /// <param name="smv">The specialized multivector for which the coordinate indices should be written.</param> public static void WriteSMVcoordIndices(StringBuilder SB, Specification S, G25.SMV smv) { SB.AppendLine(""); for (int i = 0; i < smv.NbNonConstBasisBlade; i++) { // write comment about what the #define is SB.AppendLine("/** index of coordinate for " + smv.NonConstBasisBlade(i).ToString(S.m_basisVectorNames) + " in " + smv.Name + ".c */"); SB.AppendLine("#define " + GetCoordIndexDefine(S, smv, i) + " " + i); } }
/// <summary> /// Writes the <c>defines</c> for indices of the smv struct to 'SB'. For example, <c>define VECTOR_E1 0</c>. /// </summary> /// <param name="SB">Where the code goes.</param> /// <param name="S">Used for basis vector names.</param> /// <param name="FT"></param> /// <param name="smv">The specialized multivector for which the coordinate indices should be written.</param> public static void WriteSMVcoordIndices(StringBuilder SB, Specification S, FloatType FT, G25.SMV smv) { string className = FT.GetMangledName(S, smv.Name); SB.AppendLine("\t/// Array indices of " + className + " coordinates."); SB.AppendLine("\ttypedef enum {"); for (int i = 0; i < smv.NbNonConstBasisBlade; i++) { SB.AppendLine("\t\t/// index of coordinate for " + smv.NonConstBasisBlade(i).ToString(S.m_basisVectorNames) + " in " + className); SB.AppendLine("\t\t" + GetCoordIndexDefine(S, FT, smv, i) + " = " + i + ", "); } SB.AppendLine("\t} ArrayIndex;"); }
/// <summary> /// Writes code for abs largest coordinate /// </summary> /// <param name="S"></param> /// <param name="cgd">Results go here. Also intermediate data for code generation. Also contains plugins and cog.</param> public static void WriteLargestCoordinateFunctions(Specification S, G25.CG.Shared.CGdata cgd, G25.FloatType FT, G25.SMV smv) { StringBuilder defSB = cgd.m_defSB; defSB.AppendLine(""); const string smvName = G25.CG.Shared.SmvUtil.THIS; const bool ptr = false; string fabsFunc = G25.CG.Shared.CodeUtil.OpNameToLangString(S, FT, RefGA.Symbolic.UnaryScalarOp.ABS); string[] AS = G25.CG.Shared.CodeUtil.GetAccessStr(S, smv, smvName, ptr); RefGA.BasisBlade maxBasisBlade = smv.AbsoluteLargestConstantBasisBlade(); //string className = FT.GetMangledName(S, smv.Name); for (int _returnBitmap = 0; _returnBitmap <= 1; _returnBitmap++) { bool returnBitmap = (_returnBitmap != 0); // write comment int nbTabs = 1; if (returnBitmap) new G25.CG.Shared.Comment("Returns the absolute largest coordinate,\nand the corresponding basis blade bitmap.").Write(defSB, S, nbTabs); else new G25.CG.Shared.Comment("Returns the absolute largest coordinate.").Write(defSB, S, nbTabs); string funcName = Util.GetFunctionName(S, ((returnBitmap) ? "largestBasisBlade" : "largestCoordinate")); string funcDecl; if ((S.OutputCSharp()) && returnBitmap) { funcDecl = FT.type + " " + funcName + "(int bm) "; } else if ((S.OutputJava()) && returnBitmap) { funcDecl = FT.type + "[] " + funcName + "() "; } else { funcDecl = FT.type + " " + funcName + "()"; } string FINAL = (S.OutputJava()) ? "final " : ""; defSB.Append("\tpublic " + FINAL + funcDecl); { defSB.AppendLine(" {"); if ((S.OutputJava()) && returnBitmap) defSB.AppendLine("\t\tint bm;"); int startIdx = 0; if (maxBasisBlade != null) { defSB.AppendLine("\t\t" + FT.type + " maxValue = " + FT.DoubleToString(S, Math.Abs(maxBasisBlade.scale)) + ";"); if (returnBitmap) defSB.AppendLine("\t\tbm = " + maxBasisBlade.bitmap + ";"); } else { defSB.AppendLine("\t\t" + FT.type + " maxValue = " + fabsFunc + "(" + AS[0] + ");"); if (returnBitmap) defSB.AppendLine("\t\tbm = 0;"); startIdx = 1; } for (int c = startIdx; c < smv.NbNonConstBasisBlade; c++) { defSB.Append("\t\tif (" + fabsFunc + "(" + AS[c] + ") > maxValue) { maxValue = " + fabsFunc + "(" + AS[c] + "); "); if (returnBitmap) defSB.Append("bm = " + smv.NonConstBasisBlade(c).bitmap + "; "); defSB.AppendLine("}"); } if ((S.OutputJava()) && returnBitmap) { defSB.AppendLine("\t\treturn new " + FT.type + "[]{maxValue, (" + FT.type + ")bm};"); } else { defSB.AppendLine("\t\treturn maxValue;"); } defSB.AppendLine("\t}"); } } }
/// <summary> /// Returns the comment for a SMV class. /// </summary> /// <param name="S">Used for basis vector names and output language.</param> /// <param name="cgd">Not used yet.</param> /// <param name="FT">Float point type of 'SMV'.</param> /// <param name="smv">The specialized multivector for which the struct should be written.</param> /// <param name="emitCoordIndices">Whether to emit constants for array indices to coordinates.</param> public static Comment GetSmvComment(Specification S, G25.CG.Shared.CGdata cgd, FloatType FT, G25.SMV smv, bool emitCoordIndices) { StringBuilder SB = new StringBuilder(); SB.AppendLine("This class can hold a specialized multivector of type " + FT.GetMangledName(S, smv.Name) + "."); SB.AppendLine(""); SB.AppendLine("The coordinates are stored in type " + FT.type + "."); SB.AppendLine(""); if (smv.NbNonConstBasisBlade > 0) { SB.AppendLine("The variable non-zero coordinates are:"); for (int i = 0; i < smv.NbNonConstBasisBlade; i++) { SB.AppendLine(" - coordinate " + smv.NonConstBasisBlade(i).ToString(S.m_basisVectorNames) + " (array index: " + smv.GetCoordLangID(i, S, COORD_STORAGE.VARIABLES).ToUpper() + " = " + i + ")"); } } else SB.AppendLine("The type is constant."); SB.AppendLine(""); if (smv.NbConstBasisBlade > 0) { SB.AppendLine("The constant non-zero coordinates are:"); for (int i = 0; i < smv.NbConstBasisBlade; i++) SB.AppendLine(" - " + smv.ConstBasisBlade(i).ToString(S.m_basisVectorNames) + " = " + smv.ConstBasisBladeValue(i).ToString()); } else SB.AppendLine("The type has no constant coordinates."); SB.AppendLine(""); if ((smv.Comment != null) && (smv.Comment.Length > 0)) { SB.AppendLine(""); SB.AppendLine("" + smv.Comment); } return new Comment(SB.ToString()); }