@Override public final ParseTokenSimpleTensor parseToken(String expression, Parser parser) { expression = expression.replaceAll("\\{[\\s]*\\}", ""); int indicesBegin = expression.indexOf('_'), i = expression.indexOf('^'); if (indicesBegin < 0 && i >= 0) indicesBegin = i; if (indicesBegin >= 0 && i >= 0) indicesBegin = Math.min(indicesBegin, i); if (indicesBegin < 0) indicesBegin = expression.length(); String name = expression.substring(0, indicesBegin); if (name.isEmpty()) throw new ParserException("Simple tensor with empty name."); SimpleIndices indices; if (parser.isAllowSameVariance()) indices = ParserIndices.parseSimpleIgnoringVariance(expression.substring(indicesBegin)); else indices = ParserIndices.parseSimple(expression.substring(indicesBegin)); return new ParseTokenSimpleTensor(indices, name); }
@Override public String toString(OutputFormat mode) { //Initializing StringBuilder StringBuilder sb = new StringBuilder(); //Adding tensor name if (mode.is(OutputFormat.Maple) && isKroneckerOrMetric()) { if (isKronecker()) sb.append("KroneckerDelta"); else sb.append("g_"); } else sb.append(name); //If there are no indices return builder content if (indices.size() == 0) return sb.toString(); //Writing indices boolean external = mode.is(OutputFormat.WolframMathematica) || mode.is(OutputFormat.Maple); if (external) sb.append("["); sb.append(indices.toString(mode)); if (external) sb.append("]"); return sb.toString(); } }
@Override public String toString() { StringBuilder sb = new StringBuilder(); sb.append(super.toString()).append('['); for (ParseToken node : content) sb.append(node.toString()).append(", "); sb.deleteCharAt(sb.length() - 1).deleteCharAt(sb.length() - 1).append(']'); return sb.toString(); }
@Override public ParseToken transform(ParseToken node) { TokenType type = node.tokenType; switch (type) { case SimpleTensor: ParseTokenSimpleTensor st = (ParseTokenSimpleTensor) node; NameAndStructureOfIndices ds = st.getIndicesTypeStructureAndName(); return new ParseTokenSimpleTensor(transformIndices(st.getIndices(), ds), transformer.newName(ds.getName(), ds)); case TensorField: ParseTokenTensorField tf = (ParseTokenTensorField) node; ParseToken[] newContent = transformContent(tf.content); SimpleIndices[] newArgsIndices = new SimpleIndices[tf.argumentsIndices.length]; for (int i = newArgsIndices.length - 1; i >= 0; --i) newArgsIndices[i] = IndicesFactory.createSimple(null, newContent[i].getIndices()); NameAndStructureOfIndices dsf = tf.getIndicesTypeStructureAndName(); return new ParseTokenTensorField(transformIndices(tf.getIndices(), dsf), transformer.newName(dsf.getName(), dsf), newContent, newArgsIndices); case Number: return node; case ScalarFunction: return new ParseTokenScalarFunction(((ParseTokenScalarFunction) node).function, transformContent(node.content)); case Expression: ParseToken[] nContent = transformContent(node.content); return new ParseTokenExpression(((ParseTokenExpression) node).preprocess, nContent[0], nContent[1]); default: return new ParseToken(node.tokenType, transformContent(node.content)); } }
case TensorField: case SimpleTensor: InsertionRule rule = mappedRules.get(((ParseTokenSimpleTensor) node).getIndicesTypeStructureAndName()); if (rule != null) return new SimpleTransformer((ParseTokenSimpleTensor) node,
public SimpleTransformer(ParseTokenSimpleTensor node, InsertionRule insertionRule) { this.node = node; //this.insertionRule = insertionRule; StructureOfIndices originalStructure = insertionRule.originalStructureAndName.getStructure()[0]; StructureOfIndices currentStructure = node.getIndicesTypeStructureAndName().getStructure()[0]; for (IndexType type : insertionRule.indicesAllowedToOmit) if (currentStructure.getStates(type).size() == 0) { BitArray originalStates = originalStructure.getStates(type); if (originalStates != null) { outerIndices.upper[type.getType()] = originalStates.bitCount(); outerIndices.lower[type.getType()] = originalStates.size() - outerIndices.upper[type.getType()]; } else { outerIndices.upper[type.getType()] = outerIndices.lower[type.getType()] = originalStructure.typeCount(type.getType()) / 2; } } else if (currentStructure.typeCount(type.getType()) != originalStructure.typeCount(type.getType())) throw new IllegalArgumentException(); outerIndices.init(); }
private ParseToken addDeltas(OuterIndices inserted, ParseToken node, OuterIndices expected, int[][] upper, int[][] lower) { List<ParseToken> multipliers = new ArrayList<>(); for (byte i = 0; i < TYPES_COUNT; ++i) { if (!inserted.initialized[i] && expected.initialized[i]) { if (expected.lower[i] == 0 && expected.upper[i] == 0) continue; if (expected.lower[i] != 1 || expected.upper[i] != 1) throw new IllegalArgumentException("Deltas insertion is only supported for one upper and " + "one lower omitted indices; node: " + node); multipliers.add(new ParseTokenSimpleTensor(IndicesFactory.createSimple(null, upper[i][0], lower[i][0]), CC.current().getKroneckerName())); } } if (multipliers.isEmpty()) return node; multipliers.add(node); return new ParseToken(TokenType.Product, multipliers.toArray(new ParseToken[multipliers.size()])); } }
public static ParseToken tensor2AST(Tensor tensor) { if (tensor instanceof TensorField) { TensorField tf = (TensorField) tensor; ParseToken[] content = new ParseToken[tf.size()]; int i = 0; for (Tensor t : tf) content[i++] = tensor2AST(t); return new ParseTokenTensorField(tf.getIndices(), tf.getStringName(), content, tf.getArgIndices()); } if (tensor instanceof SimpleTensor) { SimpleTensor st = (SimpleTensor) tensor; return new ParseTokenSimpleTensor(st.getIndices(), st.getStringName()); } if (tensor instanceof Complex) return new ParseTokenNumber((Complex) tensor); if (tensor instanceof Expression) return new ParseTokenExpression(false, tensor2AST(tensor.get(0)), tensor2AST(tensor.get(1))); ParseToken[] content = new ParseToken[tensor.size()]; int i = 0; for (Tensor t : tensor) content[i++] = tensor2AST(t); if (tensor instanceof ScalarFunction) return new ParseTokenScalarFunction(tensor.getClass().getSimpleName(), content); return new ParseToken(TokenType.valueOf(tensor.getClass().getSimpleName()), content); }