forums.silverfrost.com Forum Index forums.silverfrost.com
Welcome to the Silverfrost forums
 
 FAQFAQ   SearchSearch   MemberlistMemberlist   UsergroupsUsergroups   RegisterRegister 
 ProfileProfile   Log in to check your private messagesLog in to check your private messages   Log inLog in 

Using centre@ function
Goto page 1, 2  Next
 
Post new topic   Reply to topic    forums.silverfrost.com Forum Index -> General
View previous topic :: View next topic  
Author Message
PaulHolden



Joined: 08 Jan 2018
Posts: 6

PostPosted: Mon Jan 08, 2018 2:49 pm    Post subject: Using centre@ function Reply with quote

Is there a "correct" way to wrap the Centre@ function in another function using Fortran 90/95? Centre@ returns a string of length determined by the assignment statement which cannot easily be replicated in code (at least I can't find an obvious way). Many years ago I vaguely remember a newsgroup question on a similar topic in which one of the elder statesmen of Fortran said that this sort of this was not within the scope (or desirability) of the F90 standard.

Before anyone asks, I am trying to create a portability wrapper so the main code can be compiled in various compilers including FTN95.
Back to top
View user's profile Send private message
LitusSaxonicum



Joined: 23 Aug 2005
Posts: 1844
Location: Yateley, Hants, UK

PostPosted: Mon Jan 08, 2018 3:39 pm    Post subject: Reply with quote

One lives and learns - I never knew such a function existed.

Surely it is a matter of positioning the input string STRING in a character variable of length LW (as in FTN95.CHM) by (LW-LEN_TRIM(STRING))/2 from the start of the output string? (and therefore not difficult).

Eddie
Back to top
View user's profile Send private message
PaulLaidler
Site Admin


Joined: 21 Feb 2005
Posts: 5501
Location: Salford, UK

PostPosted: Mon Jan 08, 2018 4:01 pm    Post subject: Reply with quote

Also I suspect that the length of the result is determined by the declaration of CENTRE@ and not by an assignment statement. For example

Code:
CHARACTER (LEN=80) CENTRE@
Back to top
View user's profile Send private message
PaulHolden



Joined: 08 Jan 2018
Posts: 6

PostPosted: Mon Jan 08, 2018 5:44 pm    Post subject: Re: Reply with quote

LitusSaxonicum wrote:
One lives and learns - I never knew such a function existed.

Surely it is a matter of positioning the input string STRING in a character variable of length LW (as in FTN95.CHM) by (LW-LEN_TRIM(STRING))/2 from the start of the output string? (and therefore not difficult).

Eddie


All very well, but how do you define the return type of the function if you don't know the length of the string being assigned to?
Back to top
View user's profile Send private message
PaulLaidler
Site Admin


Joined: 21 Feb 2005
Posts: 5501
Location: Salford, UK

PostPosted: Mon Jan 08, 2018 5:49 pm    Post subject: Reply with quote

I am assuming that somewhere in your code there is a declaration of the form

Code:
CHARACTER (LEN=80) CENTRE@
Back to top
View user's profile Send private message
PaulHolden



Joined: 08 Jan 2018
Posts: 6

PostPosted: Mon Jan 08, 2018 5:52 pm    Post subject: Re: Reply with quote

PaulLaidler wrote:
I am assuming that somewhere in your code there is a declaration of the form

Code:
CHARACTER (LEN=80) CENTRE@


No. I am writing a wrapper function which doesn't know the length of the string being passed to Centre@. That is the problem.
Back to top
View user's profile Send private message
PaulLaidler
Site Admin


Joined: 21 Feb 2005
Posts: 5501
Location: Salford, UK

PostPosted: Mon Jan 08, 2018 6:19 pm    Post subject: Reply with quote

Perhaps the easiest solution is to use Eddie's approach.
Back to top
View user's profile Send private message
PaulHolden



Joined: 08 Jan 2018
Posts: 6

PostPosted: Mon Jan 08, 2018 7:05 pm    Post subject: Re: Reply with quote

PaulLaidler wrote:
Perhaps the easiest solution is to use Eddie's approach.

"Eddie's approach" didn't seem to answer the problem of not knowing the length of the input string at compile time. I tried several different ways to copy the runtime length of the input string dummy argument to the function return length, but none of them worked. I was hoping someone could come up with a solution.

My current "easiest" solution is to replace Centre@ function with a F90/F95 portable subroutine that does in code what Centre@ does intrinsically. It is a bit messier to call as you need 2 lines of code where the function does the same in one line, but it does at least do what I want. I guess the Centre@ function is a bit "too good to be true" and can't be replicated in a portable way.


Last edited by PaulHolden on Thu Jan 11, 2018 11:58 pm; edited 1 time in total
Back to top
View user's profile Send private message
wahorger



Joined: 13 Oct 2014
Posts: 467
Location: Morrison, CO, USA

PostPosted: Tue Jan 09, 2018 12:37 am    Post subject: Reply with quote

Is the single statement use of a function *REQUIRED* to happen, or can you use a subroutine call?

Something of the form of:

Code:

        CALL CENTRE_CALL(OLD_STRING,NEW_CENTERED_STRING)


should work just fine, and can easily be made size independent in the subroutine.

Code:

    USE MSWIN
    CHARACTER*20:: ABCD="THIS IS A TEST"
    CHARACTER(LEN=LEN(ABCD)*2) DEFG
    CHARACTER(LEN=LEN(DEFG)),EXTERNAL:: CENTRE@
    CHARACTER*10:: OLD='OLDDATA'
    CHARACTER*20:: NEWEST=' '
    DEFG = CENTRE@(ABCD,LEN(DEFG))
    PRINT *,'"',ABCD,'"'
    PRINT *,'"',DEFG,'"'
    CALL CENTRE_CALL(OLD,NEWEST)
    STOP
    END
    SUBROUTINE CENTRE_CALL(OLD,NEWEST)
    CHARACTER*(*) OLD
    CHARACTER*(*) NEWEST
    CHARACTER(LEN=LEN(NEWEST)),EXTERNAL:: CENTRE@
    INTEGER*2:: I
    I=LEN(NEWEST)
    NEWEST=' ' ! THIS MUST BE HERE, BUT SHOULDN'T NEED TO BE
    NEWEST = CENTRE@(OLD,I)
    PRINT *,'"',OLD,'"'
    PRINT *,'"',NEWEST,'"'
    RETURN
    END


Setting NEWEST to blank should not have to be there (it is initialized in the MAIN routine), but without it, things don't work right.

Also, having to use I works, but replacing it with int(len(newest),2) to set the type properly didn't work.
Back to top
View user's profile Send private message Visit poster's website
PaulHolden



Joined: 08 Jan 2018
Posts: 6

PostPosted: Thu Jan 11, 2018 8:08 pm    Post subject: Reply with quote

Thanks wahorger. The subroutine isn't as convenient as a function but it seems to be the only solution.
Back to top
View user's profile Send private message
John-Silver



Joined: 30 Jul 2013
Posts: 914
Location: Aerospace Valley

PostPosted: Fri Jan 12, 2018 7:38 am    Post subject: Reply with quote

does %cn instead of centre@ present a possible preferable solution option ?
Back to top
View user's profile Send private message
PaulHolden



Joined: 08 Jan 2018
Posts: 6

PostPosted: Fri Jan 12, 2018 7:52 pm    Post subject: Re: Reply with quote

John-Silver wrote:
does %cn instead of centre@ present a possible preferable solution option ?


The idea is to make a portable function and %cn is certainly not that. I can easily reproduce the centering in subroutine code and avoid centre@ altogether, but not as a function.
Back to top
View user's profile Send private message
John-Silver



Joined: 30 Jul 2013
Posts: 914
Location: Aerospace Valley

PostPosted: Sun Jan 14, 2018 1:43 pm    Post subject: Reply with quote

I see that Paul, and that people have proposed solutions to circumvent the use of centre@, but the original question was worded as when you were still trying to use centre@, which is an ftn95 fucntion right, hence maybe equally 'incompatible' as centre@ - maybe.
So I just thought maybe %cn could actually be used with maybe no compatability problems in terms of declarations.
Clearwin is 'ported' to be useable with other fortran compilers so is useable in that sense.
Isn't .NET the politically correct route to take for platform independent (i.e. compatability) needs ?
The people at SIMPLEPLOT apparently got a case working with their code attached. Maybe that 's a route to consider/pursue in the longer term.
From what's written in the case-study concerning Simpleplot (in the documentation cěsection on website) Silverfrost wer very helpful at the time in helping them get it up and running.
Back to top
View user's profile Send private message
LitusSaxonicum



Joined: 23 Aug 2005
Posts: 1844
Location: Yateley, Hants, UK

PostPosted: Sun Jan 14, 2018 4:53 pm    Post subject: Reply with quote

If I am right (and I concede that it is about 20 years since I last worked with Assembler, so I could be wrong), then all a FUNCTION returns is the address to its result on the stack. Moreover, the result is 'forgotten' immediately after the assignment or WRITE in which the function is invoked when the stack is cleaned up.

Hence, so long as the return address is mangled to point to the string of length LW with the input STRING centered in it, then that sequence of characters ought to be picked up in the calling routine and copied (or used) for that one time. It doesn't matter where in RAM that temporary copy resides, surely, and it could reside somewhere where it was ephemeral, i.e. allocated dynamically, if you so wish.

I assume that FTN95 reserves a long enough contiguous sequence of bytes at compilation by finding the longest declaration of the length of CENTRE@ (viz. FTN95.CHM's example call), the address of which is known to it, to Paul, and all the other folk at Silverfrost who understand such things, especially if there is a statically allocated sequence just reserved for it somewhere.

Of course the best answer is not to bother with those other compilers, and stick to FTN95, but then my view is that FTN95 is the best in every respect, and others are free to differ.

Eddie
Back to top
View user's profile Send private message
mecej4



Joined: 31 Oct 2006
Posts: 981

PostPosted: Mon Jan 15, 2018 3:34 pm    Post subject: Reply with quote

Paul Holden:

I am not sure about what you require, but how about something like this?
Code:
function center(strng)
   implicit none
   character(len=*) :: strng
   character(len=(len(strng)+len_trim(strng))/2) :: center
!
! code to assemble the output string,
! with the correct number of leading blanks added and trailing blanks removed
!
end function center

You need to cut out leading blanks from the argument before passing the string to this function. If that is not desirable, or you wish to keep trailing blanks in the result string, you could adjust the length in the declaration of "center" to suit your needs.


Last edited by mecej4 on Mon Jan 15, 2018 4:40 pm; edited 2 times in total
Back to top
View user's profile Send private message
Display posts from previous:   
Post new topic   Reply to topic    forums.silverfrost.com Forum Index -> General All times are GMT + 1 Hour
Goto page 1, 2  Next
Page 1 of 2

 
Jump to:  
You cannot post new topics in this forum
You cannot reply to topics in this forum
You cannot edit your posts in this forum
You cannot delete your posts in this forum
You cannot vote in polls in this forum


Powered by phpBB © 2001, 2005 phpBB Group