From: aborel on 7 Jan 2008 16:50 Good evening I am writing a program which mainly converts text input files in different file formats (ASCII) as input for FEM Pre-and Postprocessors. The program reads the input data in an array (init_material_data) of the type material_data and then writes the data in a different file format doing different conversions. Due to the different maximum lengths of the input variables I have to use of a derived type variable which is in module "defs". ! ! module defs ! implicit none ! type material_data character(8) :: id character(256) :: name character(2) :: type character(10) :: info1 character(10) :: info2 character(12), dimension(25) :: mat_data end type material_data ! type(material_data), pointer, dimension(:) :: init_mat_data type(material_data) :: iso_mat_data ! end module defs ! ! Now I searched my books and this group for a description of how to initialize above derived type "init_mat_data" but the only way I can imagine would be do m=1,n_rows,1 init_mat_data(m)%id = "xx" init_mat_data(m)%name = "xx" init_mat_data(m)%type = "xx" init_mat_data(m)%info1 = "xx" init_mat_data(m)%info2 = "xx" do j=1,25,1 init_mat_data(m)%mat_data(j) = "xx" end do end do at run time. The same with the derived type iso_mat_data. Is there any more elegant way of solving this problem, it seems to me that my solution is not very efficient... Thank you for any answer (I am a "free time programmer" and this will surely increase my programming skills...) Regards Alex
From: Paul van Delst on 7 Jan 2008 17:36 aborel(a)pilatus-aircraft.com wrote: > Good evening > I am writing a program which mainly converts text input files in > different file formats (ASCII) as input for FEM Pre-and > Postprocessors. > The program reads the input data in an array (init_material_data) of > the type material_data and then writes the data in a different file > format doing different conversions. > Due to the different maximum lengths of the input variables I have to > use of a derived type variable which is in module "defs". > ! > ! > module defs > ! > implicit none > ! > type material_data > character(8) :: id > character(256) :: name > character(2) :: type > character(10) :: info1 > character(10) :: info2 > character(12), dimension(25) :: mat_data > end type material_data > ! > type(material_data), pointer, dimension(:) :: init_mat_data > type(material_data) :: iso_mat_data > ! > end module defs > ! > ! > > Now I searched my books and this group for a description of how to > initialize above derived type "init_mat_data" but the only way I can > imagine would be > > do m=1,n_rows,1 > > init_mat_data(m)%id = "xx" > init_mat_data(m)%name = "xx" > init_mat_data(m)%type = "xx" > init_mat_data(m)%info1 = "xx" > init_mat_data(m)%info2 = "xx" > do j=1,25,1 > init_mat_data(m)%mat_data(j) = "xx" > end do > end do > > at run time. The same with the derived type iso_mat_data. If you have a f95 compiler, you can do: type material_data character(8) :: id = 'xx' character(256) :: name = 'xx' character(2) :: type = 'xx' character(10) :: info1 = 'xx' character(10) :: info2 = 'xx' character(12), dimension(25) :: mat_data = 'xx' end type material_data and then every instance you create will be initialised. And don't forget to do, type(material_data), pointer, dimension(:) :: init_mat_data => NULL() cheers, paulv > > Is there any more elegant way of solving this problem, it seems to me > that my solution is not very efficient... > Thank you for any answer (I am a "free time programmer" and this will > surely increase my programming skills...) > > Regards Alex >
From: David Frank on 7 Jan 2008 17:41 You are allowed to initialize type members at their declaration type material_data character(8) :: id = 'id123456' ! note you can indicate format of id at same time .... end type
From: Richard Maine on 7 Jan 2008 18:01 <aborel(a)pilatus-aircraft.com> wrote: > Good evening > I am writing a program which mainly converts text input files in > different file formats (ASCII) as input for FEM Pre-and > Postprocessors. > The program reads the input data in an array (init_material_data) of > the type material_data and then writes the data in a different file > format doing different conversions. > Due to the different maximum lengths of the input variables I have to > use of a derived type variable which is in module "defs". > ! > ! > module defs > ! > implicit none > ! > type material_data > character(8) :: id > character(256) :: name > character(2) :: type > character(10) :: info1 > character(10) :: info2 > character(12), dimension(25) :: mat_data > end type material_data > ! > type(material_data), pointer, dimension(:) :: init_mat_data > type(material_data) :: iso_mat_data > ! > end module defs > ! > ! > > Now I searched my books and this group for a description of how to > initialize above derived type "init_mat_data" but the only way I can > imagine would be > > do m=1,n_rows,1 > > init_mat_data(m)%id = "xx" > init_mat_data(m)%name = "xx" > init_mat_data(m)%type = "xx" > init_mat_data(m)%info1 = "xx" > init_mat_data(m)%info2 = "xx" > do j=1,25,1 > init_mat_data(m)%mat_data(j) = "xx" > end do > end do > > at run time. The same with the derived type iso_mat_data. > > Is there any more elegant way of solving this problem, it seems to me > that my solution is not very efficient... If you are just worried about the efficiency, I'd stop worrying. You aren't going to be able to measure any efficiency difference. I'd place money on it. This won't take enough time to matter, no matter how you do it. In fact, if the array is large enough for the time to be measurable, there are at least decent odds that doing it at run-time like this might be faster than doing it with static initialization. Static initialization of large arrays tends to involve storing those arrays in the executable file, which makes for large executable files. Reading the data from that executable image into memory involves disk I/O, which is several orders of magnitude slower than CPU and memory operations. Just because you don't see a loop in your code, don't think that means that things happen by magic and are automatically free of cost. That being said, I'll offer some possible alternatives, but don't think these will improve efficiency. You might consider some of them to improve elegance. 1. I see that your init-mat_data is a pointer. That's fine, but note that it is incompatible with compile-time initialization. You can't ever initialize a pointer to anything other than nullified. I assume that you allocate or assign the pointer somewhere. 2. Along the same lines, I wonder whether making it allocatable might be more appropriate than making it a pointer. That won't allow compile-time initialization, but many would consider it more "elegant" than using a pointer. Allocatables are less error-prone and generally more efficient than pointers unless you are really doing things that require the extra functionality of pointers. 3. I would suggest that the most "elegant" way to initialize these objects would be to use what is called default initialization. You set this up with the type definition and it then applies to all objects of the type. Thus, it is not appropriate for initializing individual objects of the type with different values. There is only one initial default value that applies to all objects of the type. But from your example, that looks like what you are doing anyway. You'd do this something like type material_data character(8) :: id = "xx" character(256) :: name = "xx" character(2) :: type = "xx" character(10) :: info1 = "xx" character(10) :: info2 = "xx" character(12), dimension(25) :: mat_data = "xx" end type material_data The default initialization will be applied whenever an object of the type is "created". For an allocatable array (or a pointer array that gets allocated), that will be when you do the allocation. 4. Note that in the default initialization for the mat_data component above, I have taken advantage of the feature that allows you to assign a scalar value to an array. The scalar gets propogated to every element of the array. That is independent of default initialization. You can use it in other contexts as well. For example, in your sample code above, you could replace > do j=1,25,1 > init_mat_data(m)%mat_data(j) = "xx" > end do with init_mat_data(m)%mat_data "xx" It does the same thing. The loop is just implied. I'd consider it slightly more "elegant", though opinions on that vary. (Some people like making the array nature more explicit; I don't.) 5. The other feature that you might possibly be looking for is what is called a structure constructor. It does allow you to put all this into a single statement. I personally wouldn't do it that way, because I'd find that single statement harder to read than the way that you spelled it out. But if you really wanted to do that, it could look something like init_mat_data = material_data("xx","xx","xx","xx","xx") where I have also made use (twice) of the automatic expansion of scalars into arrays. You could spell the arrays out with array constructors, but that would make this a lot more long-winded. This is probably the closest thing to what you were asking for. You can even use this form in a static initialization (although not for a pointer or allocatable). -- Richard Maine | Good judgement comes from experience; email: last name at domain . net | experience comes from bad judgement. domain: summertriangle | -- Mark Twain
From: Michael Metcalf on 8 Jan 2008 08:59 <aborel(a)pilatus-aircraft.com> wrote in message news:aee4286b-22d3-4425-aced-797e370294ea(a)k39g2000hsf.googlegroups.com... > Now I searched my books and this group for a description of how to > initialize above derived type "init_mat_data" .... "Fortran 95/2003 Explained", Sections 7.5.3 and 7.5.4. Regards, Mike Metcalf
|
Next
|
Last
Pages: 1 2 3 Prev: gfortran and ifort gave the different result. Next: not able to use gnuplotfortran .... |