Consider the following sample:
ie = 200; ez = ConstantArray[0., {ie + 1}]; hy = ConstantArray[0., {ie}]; fdtd1d = Compile[{{steps}}, Module[{ez = ez, hy = hy}, Do[ez[[2 ;; -2]] += hy[[2 ;; -1]] - hy[[1 ;; -2]]; ez[[1]] = Sin[n/10]; hy[[1 ;; -1]] += ez[[2 ;; -1]] - ez[[1 ;; -2]], {n, steps}]; ez]]; fdtd1d[1000]; // AbsoluteTiming {0.0100000, Null}
Apparently there're 2 sentences (of course in real situation there can be more) with same structure that can be represented with a function if fdtd1d is built with Function:
ie = 200; ez = ConstantArray[0., {ie + 1}]; hy = ConstantArray[0., {ie}]; ClearAll[f]; SetAttributes[f, HoldFirst] f[list1_, list2_, end_] := list1[[end ;; -end]] += (list2[[2 ;; -1]] - list2[[1 ;; -2]]); fdtd1d = Function[{steps}, Module[{ez = ez, hy = hy}, Do[f[ez, hy, 2]; ez[[1]] = Sin[n/10.]; f[hy, ez, 1], {n, steps}]; ez]]; fdtd1d[1000]; // AbsoluteTiming {0.1050000, Null}
But this method isn't available for Compile, even with the trick mentioned here:
ie = 200; ez = ConstantArray[0., {ie + 1}]; hy = ConstantArray[0., {ie}]; ClearAll[f]; f = Function[{list1, list2, end}, list1[[end ;; -end]] += (list2[[2 ;; -1]] - list2[[1 ;; -2]]), HoldFirst]; fdtd1d = Compile[{steps}, Module[{ez = ez, hy = hy}, Do[f[ez, hy, 2]; ez[[1]] = Sin[n/10.]; f[hy, ez, 1], {n, steps}]; ez], CompilationOptions -> {"InlineExternalDefinitions" -> True}]; << CompiledFunctionTools` CompilePrint@fdtd1d Compile::argset: The assignment to Compile`FunctionVariable$1571 is illegal; it is not valid to assign a value to an argument. >>
…… 1 Return Error
So, as the title said, is there a way to make the code inside Compile conciser without performance decreasing or even compilation failure?