ANSYS: how to organize my code? - simulation

I'm using ANSYS to analyse a basic structure, and I need to switch between dynamic analysis, static analysis. And sometimes I need to only consider a certain load. This makes the solution part in a mess.
!!! Add wind loads
*DIM,windforce,,4
windforce(1) = 2520
windforce(2) = -1575
windforce(3) = -1890
windforce(4) = -1575
*DO,i,1,3
SFBEAM,i ,1 ,PRES ,windforce(1)
*enddo
*DO,i,4,6
SFBEAM,i ,1 ,PRES ,windforce(2)
*enddo
*DO,i,7,9
SFBEAM,i ,1 ,PRES ,windforce(3)
*enddo
*DO,i,10,12
SFBEAM,i ,1 ,PRES ,windforce(4)
*enddo
FINISH
/SOLU ! enter solution phase
! !!Dynamic Analysis
! antype,modal
! modopt,lanb,40,0,0,,off
! mxpand,0,,,0
! lumpm,1
! solve
! finish
! ! ! Generate Mass and K Matrix
! antype,substr
! seopt,yg_bde,2
! lumpm,1
! m,all,all
! /output,matrix
! solve
! /output
! selist,yg_bde,3
! finish
SOLVE ! solve the resulting system of equations
FINISH
Everytime I swtich between this analysis, I need to comment in/out a big chuck of code. And this looks really terrible.
So How can I organize my code? Or how to make this code modulize? Is there any framework for ANSYS scripting language? (Like scss for css).

I don't think there is exactly such tool, but there is a list of Ansys approved text editors and other helpful programs (digitizers, CAD converters e.t.c).
I guess, if there will be any good framework, it must be listed there.

I suggest to use chunks of code in separate files and then call on these files in main code.
Simplest way to switch parts of code is to use *IF condition in combination with argument. Then you can call on your script as myscript.txt,ARG1,ARG2,ARG3.. where myscript.txt is your script name (also .ans,.mac ...) and ARGx are your switches.
Sample:
! here is the same stuff for any run
*IF,ARG1,EQ,1,then
! here is one variation of the code (e.g. static analysis)
*ENDIF
*IF,ARG1,EQ,2,then
! here is another variation of the code (e.g. dynamic analysis)
*ENDIF
! here is again code used for any variation of the code
If the sample above is in text file called solverswitch.txt, then you would execute various solver options via solverswitch.txt,1 (or solverswitch.txt,2)

I use jedit to edit complex ANSYS files, it recognizes most ANSYS commands and color-codes them for easy reference, besides having various typical functionalities of scripting software.
You have to rename your input files *.ans so that jedit recognizes the ANSYS format.
I'm not sure if this is what you mean by "modulize" the code, but you can create various scripts and call them from a main routine with the command
/INPUT,'file_name','file_extension','relative_path',,0

I work mainly with bridges and I frequently have to do multiple types of analyses (static, dynamic, etc.). My workflow is a base APDL file, e.g. "truss_bridge.txt" which calls other files: "bridge_load.txt", "bridge_design.txt", "bridge_out.txt" for different types of analyses, meshing, outputs, respectively.
I separate these different options inside of each file with the /EOF command and call the type of analysis that I want with the /INPUT command specifying the appropriate line. So my base file for your situation could be something like:
/INPUT,viaduct_materials,txt,direct ! material parameters
/INPUT,viaduct_real_constants,txt,direct ! R.C. parameters
/INPUT,viaduct_design,txt,direct ! Design bridge and meshing
/INPUT,viaduct_load,txt,direct,1 ! LOAD File static analysis
! Post Processing
/INPUT,viaduct_out,txt,direct,1 ! Output file S.A.
/INPUT,viaduct_load,txt,direct,14 ! LOAD File dynamic analysis
! Post Processing
/INPUT,viaduct_out,txt,direct,21 ! Output file D.A.

Related

Referencing External Files in JModelica

I have a Modelica file that references c code during simulation through an external library *.a file.
For example:
model CallAdd
input Real FirstInput(start=0);
input Real SecondInput(start=0);
output Real FMUOutput(start=0);
function CAdd
input Real x(start=0);
input Real y(start=0);
output Real z(start=0);
external "C" annotation(Library = "CAdd", LibraryDirectory = "modelica://CallAdd");
end CAdd;
equation
FMUOutput = CAdd(FirstInput,SecondInput);
annotation(uses(Modelica(version = "3.2.1")));
end CallAdd;
When opening the Modelica model in OpenModelica the required files appear to be automatically loaded because it simulates and gives appropriate results.
However, when I try to compile the Modelica file with JModelica-SDK-1.12 I receive an error that the library *.a file could not be found.
So my question is: What is the proper way to reference additional files when using compile_fmu in JModelica?
With no success, I've tried:
# Import the compiler function
from pymodelica import compile_fmu
model_name = "CallAdd"
mo_file = "CallAdd.mo"
# Compile the model and save the return argument, for use later if wanted
my_fmu = compile_fmu(model_name, mo_file, target="cs",compiler_options = {'extra_lib_dirs':'C:/ToFolderContainingLib/'})
The strange thing is that when I was using JModelica-1.17 (non-SDK) the file compiled fine but the results didn't make sense. I was recommended to try the SDK version to see if it fixed my errors in my previous post here.
Try positioning the external library in sub-folder named as the platform your currently on. So in your example, I'd position the library (libCAdd.a) in sub-folder named linux64, as I'm on a 64bit Linux machine and then run the code.
If is a small piece of C code, as a last alternative you could try to include the C file directly in the Modelica code:
external "C" annotation(Include="
// the entire C code here
");
Hopefully the JModelica people will give you a better answer soon.
You could try to ask this on their website also:
http://www.jmodelica.org/forum

How can I make sure that Matlab mcc doesn't build incomplete stand-alone executables?

we use a scripting environment to automatically build, run and verify a stand-alone executable. We are working with Matlab R2010a x64. The Matlab compiler mcc is called from the Windows command line building a stand-alone application:
mcc -m -v -w enable -I source_folder -I common_folder -a specific_files_we_need our_program
The program consists of about 25 modules (.m files) and is using about 5 toolboxes. This is working fine as long as the correct license is available. mcc checks for a compiler license available, resolves dependencies, packs everything in the executable.
However if the license does not include the required toolboxes, mcc does not issue any warning or error. It builds the executable without the toolboxes. So the executable starts, seems to run at a first glance but crashes if a line of code requiring a toolbox is reached.
I am expecting from a compiler that it informs me about missing components. What can I do to get informed about missing components? How can I make sure that mcc does not put together incomplete executables? Am I missing something in the call to mcc?
Preferably I would like to setup the compiling in a way that it stops if things are missing.
\Zweikeks
The simplest way is in your compilation script you can checkout the licenses required, i.e.
license('checkout','Compiler')
license('checkout','control_toolbox')
You just add the 5 toolboxes that need to be checked out -> if the license function cant checkout the license it returns false which you can then use to abort the compilation.
This is what I finally came up with:
I can check before compilation which toolboxes are needed and call license() accordingly. Or I can implement a built-in check into the executable itself. (Called with a special parameter after compilation triggers a self-check for available toolboxes.) In either case I need the names of the required toolboxes.
I tried several ways to generate a list of toolboxes. In short: Running the program in Matlab and then entering license('inuse') is not very reliable. depfun() descends way to much. mydepfun() and fdep() do not descend enough.
I think the problem with mydepfun() and fdep() is that they do not descend into the \toolbox\shared folder. So I took mydepfun() from Tobias Kienzler (link to the original sources) and modified it:
function [list,callers,tboxes_found] = i_scan(f)
func = i_function_name(f);
[list,~,~,~,~,~,callers,~] = depfun(func,'-toponly','-quiet');
toolboxroot = fullfile(matlabroot,'toolbox');
sharedroot = strcat(toolboxroot, filesep, 'shared');
intoolbox = strncmpi(list,toolboxroot,numel(toolboxroot));
inshared = strncmpi(list,sharedroot, numel(sharedroot));
tboxes_found = list(intoolbox & ~inshared);
tboxes_found = regexpi(tboxes_found, '[\\/]toolbox[\\/](.+?)[\\/]', 'tokens');
tboxes_found = cellfun(#(cfun) cfun{1}, tboxes_found);
list = list(~intoolbox | inshared);
callers = callers(~intoolbox | inshared);
for jj = 1:numel(list)
c = callers{jj};
cs = cell(numel(c),1);
for kk = 1:numel(c)
cs{kk} = list{c(kk)};
end;
callers{jj} = cs;
end;
This way i_scan(f) is returning the toolboxes and also descends into \toolbox\shared. The main function of mydepfun() just collects the toolboxes:
function [filelist,callers,toolboxes] = mydepfun(fn,recursive)
.
.
toolboxes = {};
[filelist,callers,tboxes_found] = i_scan(foundfile);
toolboxes = [toolboxes; tboxes_found];
.
.
[newlist,newcallers,tboxes_found] = i_scan(toscan{1});
toolboxes = [toolboxes; tboxes_found];
.
.
toolboxes = unique(toolboxes);
The toolboxes listed are the ones our source code uses. The modified mydepfun() seems to work fine. (Apart from the typical problems caused by elements only resolved during run time like eval(), function handles, callbacks etc.)
And: The dependeny walkers I have seen - like mydepfun() - are using depfun() inside. depfun() is not reliable since it silently ignores all source code not on the path (also its return prob_files is empty in this case). So care has to be taken that the Matlab path is set correctly. (Also any additional pathes are problematic since Matlab may take unexpectedly functions with the same name from other locations.)
After all, I think, this is a good way to make my build process more reliable.
/Zweikeks
I just got another hint from the Mathworks forum. The compiler writes out mccExludedFiles.log. This is listing missing toolboxes.
For example
mccExludedFiles.log:
C:\Program Files\MATLAB\R2010a\toolbox\shared\optimlib\fmincon.m
called by ...c:\temp\whatever\source\code.m
(because the required licenses are not available.)
(Other missing files in the source code do not get listed, though.)
/Zweikeks

What is the full command for gdal_calc in ipython?

I've been trying to use raster calculation in ipython for a tif file I have uploaded, but I'm unable to find the whole code for the function. I keep finding examples such as below, but am unsure how to use this.
gdal_calc.py -A input.tif --outfile=result.tif --calc="A*(A>0)" --NoDataValue=0
I then tried another process by assigning sections, however this still doesn't work (code below)
a = '/iPythonData/cstone/prec_7.tif'
outfile = '/iPythonData/cstone/prec_result.tif'
expr = 'A<125'
gdal_calc.py -A=a --outfile=outfile --calc='expr' --NoDataValue=0
It keeps coming up with can't assign to operator. Can someone please help with the whole code.
Looking at the source code for gdal_calc.py, the file is only about 300 lines. Here is a link to that file.
https://raw.githubusercontent.com/OSGeo/gdal/trunk/gdal/swig/python/scripts/gdal_calc.py
The punchline is that they just create an OptionParser object in main and pass it to the doit() method (Line 63). You could generate the same OptionParser instance based on the same arguments you pass to it via the command-line and call their doit method directly.
That said, a system call is perfectly valid per #thomas-k. This is only if you really want to stay in the Python environment.

How to reliably detect os/platform in Go

Here's what I'm currently using, which I think gets the job done, but there's got to be a better way:
func isWindows() bool {
return os.PathSeparator == '\\' && os.PathListSeparator == ';'
}
As you can see, in my case all I need to know is how to detect windows but I'd like to know the way to detect any platform/os.
Play:
http://play.golang.org/p/r4lYWDJDxL
Detection at compile time
If you're doing this to have different implementations depending on the OS, it is more useful to
have separate files with the implementation of that feature and add build tags to each
of the files. This is used in many places in the standard library, for example in the os package.
These so-called "Build constraints" or "Build tags" are explained here.
Say you have the constant PATH_SEPARATOR and you want that platform-dependent, you
would make two files, one for Windows and one for the (UNIX) rest:
/project/path_windows.go
/project/path_unix.go
The code of these files would then be:
path_windows.go
// +build windows
package project
const PATH_SEPARATOR = '\\'
path_unix.go
// +build !windows
package project
const PATH_SEPARATOR = '/'
You can now access PATH_SEPARATOR in your code and have it platform dependant.
Detection at runtime
If you want to determine the operating system at runtime, use the runtime.GOOS
variable:
if runtime.GOOS == "windows" {
fmt.Println("Hello from Windows")
}
While this is compiled into the runtime and therefore ignores the environment,
you can nevertheless be relatively certain that the value is correct.
The reason for this is that every platform that is worth distinguishing needs
rebuilding due to different executable formats and thus has a new GOOS value.
Have you looked at the runtime package? It has a GOOS const: http://golang.org/pkg/runtime/#pkg-constants
It's 2022 and the correct answer for go 1.18+ is:
At runtime you want:
if runtime.GOOS == "windows" {
// windows specific code here...
}
If you need to determine the filesystem path separator character
Use: os.PathSeparator
Examples:
c:\program files
/usr/local/bin
If you need the Path List separator as used by the PATH environment variable
Use: os.PathListSeparator
Examples:
/usr/local/bin:/usr/local:
"C:\windows";"c:\windows\system32";
Since this is an older question and answer I have found another solution.
You could simply use the constants defined in the os package. This const returns a rune so you would need to use string conversion also.
string(os.PathSeparator)
string(os.PathListSeparator)
Example: https://play.golang.org/p/g6jnF7W5_pJ
I just stumbled on this looking for something else and noticed the age of this post so I'll add a more updated addition. If you're just trying to handle the correct filepath I would use filepath.Join(). Its takes all of the guesswork out of os issues. If there is more you need, other than just filepath, using the runtime constants (runtime.GOOS & runtime.GOARCH) are the way to go: playground example
I tested in Go 1.17.1 which really worked for me.
package main
import (
"fmt"
"runtime"
)
func main(){
fmt.Println(runtime.GOOS)
}
Output:
darwin
With regards to detecting the platform, you can use Distribution Detector project to detect the Linux distribution being run.
The first answer from #nemo is the most apropiate, i just wanted to point out that if you are currently a user of gopls language server the build tags may not work as intended.
There's no solution or workaround up to now, the most you can do is change your editor's lsp configs (vscode, neovim, emacs, etc) to select a build tag in order to being able to edit the files with that tag without errors.
Editing files with another tag will not work, and trying to select multiple tags fails as well.
This is the current progress of the issue github#go/x/tools/gopls

Data.c file generation

i'm very new to matlab, i'm working on a software which needs the following files as input model.c,model.h,model_data.c for a particular simulink model. I have a model for which i can't generate model_data file using RTW, i have tried to get some information on the files generated by RTW, but i didnt get sufficient info. If there anybody who knows about the RTW please let me know the blocks which are required to generate model_data.c
thank you
model_data.c is a conditionally created file (i.e. it is only created if it is needed, which depends on the way the model is set up for code generation).
For a discussion of the Simulink Coder build process, and what files get generated when, search the doc for the section titled "Files and Folders Created by Build Process".
For others who need help in future.
Open the Configuration Parameters pane. Go to Code Generation -> Optimization and make sure that Default parameter behavior is set to Tunable.