I have an array which holds a record from a CSV file. Can I for example use the move statement to move elements 5 to 10 out into working storage? Something like: MOVE ExampleArray(5:10) TO WS-TEST. I have been told this is possible instead of having to loop through the array. But I can not seem to get it to compile this way.
The syntax you are using is called Reference Modification. It is the equivalent of substring() in other languages. Your example code would try to move 10 bytes from ExampleArray+5.
There is a "ALL" subscript concept that is supported. It has limitations, but it MIGHT do what you want. Try something like:
Move ExampleArray(ALL) to WS-Test
Depending upon your compiler, it MIGHT work. I think the spec limits its use to integer functions, but not all compilers do.
Seriously though, perform loops are very simple and easy, just code this:
Perform varying II from 1 by 1
until II > (Length of ExampleArray-Area / Length of ExampleArray(1))
Move ExampleArray(II) to WS-Test(II)
End-Perform
Related
I have a lot of music chords that can have alternate names, rather than having to create longer lines with a lot of == and or's for each alternate name, and if chord=="Maj" or "maj" or.. don't work with Lua:
if chord=="Maj9" or chord="maj9" or chord=="M9" or chord=="Maj7(add9)" or chord=="M7(add9)" then notes="0,4,7,11,14" end
I need a simpler way to do it, maybe just reformat the lines in Notepad++ to use an array,
at the moment each of the 200+ chords on one line each:
if chord=="Maj9,maj9,M9,Maj7(add9),M7(add9)" then notes="0,4,7,11,14" end
if chord=="mMaj7,minmaj7,mmaj7,min/maj7,mM7,m(addM7),m(+7),-(M7)" then notes="0,3,7,11" end
The correct way is to normalize your input. For example, take whatever chord value comes in and use Lua’s string.lower() function to make the string all lowercase. By normalizing your input, you simplify the logic you need to write to work with that data. Consider other ways as well to normalize the data. You might, for example, write a method that converts all notes into an enumerated list (C = 1, C# = 2, etc.). That way equivalent notes get the same in-memory values.
Those are just a few ideas to get you on track. You should not try to think up and then hard-code every possible way a user may input a chord name.
Full disclosure, my question is pertaining to a project I am working on for my Data Structures class. I know this is usually frowned upon, but I am hoping it may be okay due to the fact that I have the data structure itself done and I'm just seeking assistance in creating a method.
The project is to implement a custom data structure to represent unbounded integers using a custom linked list. I cannot use the BigInteger nor LinkedList classes. I implemented the data structure using the IntNode class provided from the project.
The class takes in a string of numbers, breaks it into 3 character chunks, converts those chunks into integers and stores each chunk in a custom "linked list" of IntNode objects.
For example: 123456789123 represented as 4 IntNodes, <123> <456> <789> <123>
The method I am having difficulty implementing is:
UnboundedInt multiply (UnboundedInt )
A method that multiplies the current UnboundedInt with a passed in one. The return is a new UnboundedInt.
There is also an 'add' method which was easy to implement and I do realize I could use to handle multiplication by looping the 'add' method as many times as one of the UnboundedInt objects, however, how would I handle the loop variable when it, itself, breaches the limit of an integer?
I do realize I could use to handle multiplication by looping the 'add' method as many times as one of the UnboundedInt objects
That's not going to be the answer, because it would be too slow if either operand is non-trivial.
There is also an 'add' method which was easy to implement
That's good, because that's going to be part of the solution.
How did you implement that?
Probably following the steps you would do if you had to do it on paper.
You can implement multiplication the same way.
How do you multiply two numbers on paper?
You multiply the number on the left with each digit on the right, one by one.
After you have the multiples by one digits, you add them.
For example, let's say you were to multiply 123456789123 with 234. It would go like this:
123456789123 * 234
------------
246913578246
370370367369
+ 493827156492
==============
28888888654782
Multiplying an IntNode by 1-digit numbers should be easy,
and you already have the implementation of add, so the complete solution is not far away. To sum it up, what you still need to implement:
Multiply by a 1-digit number
Multiply by 10
Combine the above two to compute the total
Even though loops are kind of a logical concept in X12 (not directly physically represented in the text), every transaction set defines a set of loops that it can contain, including identifiers for the loops and an ordering for them. My question is, what is the rule for sorting loops, generically? Is there a concise set of rules that can be expressed in some code that should be able to take a collection of loops (with known identifiers such as 1000A, 2300BB, etc) and properly sort them?
The context of my question is that I'm working on a general-purpose library that applications will use to construct a model of an X12 document/transaction-set (and write out the text such a model represents). It has objects to represent Elements, Segments, and Loops. Ordering of Segments in a particular Loop is easy, they're dictated by the Implementation Guides. But I'm trying to get Loop ordering (within a Transaction Set) to work generically; that's what I'm asking about
It seems that the general rule is that Loops are ordered based on their identifiers using the numeric portion as the primary sort key, with the alpha portion as the secondary sort key. Of course hierarchical loops contained in others will be placed before and loops following the parent in that sort order (eg: 1000A, 2000A, 2010A, 2010B, 2100, 2300 - where 2010A and 2010B are children of 2000A).
I understand that the spec and Implementation Guides contain all of this info; I'm looking for the all-encompassing rule about loop ordering (not Segment ordering). Is there any concise way to express the rule algorithmically? Is there even a hard-and-fast rule at all?
As I mentioned in my comments, the standard has a loop value. Take a look at my screenshot of the Liaison Dictionary Viewer. The CLM segment has a LOOP value of 100. The segments underneath are children of the CLM segment (extended tag). Any "order" can be defined arbitrarily by the partner, or can be in any (undefined) order provided the data is qualified. But that loop can occur 100 times max and can have repeating segments inside the loop value.
The implementation guide will give you the correct order your partner wants them in. It seems like you're writing your own syntax validation engine though.
I have the following code snippet in one of my COBOL program.
IF FIRST < SECOND
MOVE FIRST TO WS
END-IF.
MOVE SECOND TO WS.
MOVE WS TO RESULT.
I need to use GO TO inside the IF block to jump to the last statement (MOVE WS TO RESULT).
IF FIRST < SECOND
MOVE FIRST TO WS
GO TO <last line.(MOVE WS to RESULT)>
END-IF.
MOVE SECOND TO WS.
MOVE WS TO RESULT.
in other word, i need to skip "MOVE SECOND TO WS.".
what is the simplest way to jump to a specific line in cobol?
I read somewhere that this is possible by defining a PARAGRAPH, but don't know how to define it.
It might seems very simple but I'm newbie to COBOL programming.
Thanks.
----------------* UPDATE *----------
based on #lawerence solution, is this correct?
IF FIRST < SECOND
MOVE FIRST TO WS
GO TO C10-END.
END-IF.
MOVE SECOND TO WS.
C10-END.
MOVE WS TO RESULT.
i just moved back the last statement to be in first level.
GOTO can do what you're looking for, but IF/ELSE would be more direct. You want MOVE SECOND TO WS to run iff the IF block does not, correct?
IF FIRST < SECOND
MOVE FIRST TO WS
ELSE
MOVE SECOND TO WS
END-IF.
MOVE WS TO RESULT.
I hope I got the syntax right, I have never used COBOL and just tried to work off your snippet and this example http://www.fluffycat.com/COBOL/If-and-End-If/. There probably will be situations in the future where you need GOTO, but it A) should be avoided when another control structure will work and B) I haven't the slightest idea how its done
to be honest, COBOL looks pretty miserable lol. ive never seen a language so verbose. good luck with everytihng
EDIT
Mostly for joe...
Cant this all be better done with a min function? I'm sure the syntax is wrong, but:
Move Function Min(FIRST, SECOND) to RESULT
OMFSM! It is not 1974, why are you writing Cobol like that? This:
IF FIRST < SECOND
MOVE FIRST TO WS
END-IF.
MOVE SECOND TO WS.
MOVE WS TO RESULT.
Has a number of problems:
It uses periods to delimit scope, that is nearly three decades deprecated.
It isn't using ELSE
It is trying to use GO TO.
May I suggest the following as the way to approach it since 1985:
If FIRST < SECOND
Move FIRST to WS
Else
Move SECOND to WS
End-IF
Move WS to RESULT
But really, the code should simply read:
If FIRST < SECOND
Move FIRST to RESULT
Else
Move SECOND to RESULT
End-If
Unless the intermediate result is needed in WS. Cobol 66 and 74 used GOTO and periods because they lacked modern control structures. I realize you are a 'newbie', but you should suggest to whoever is teaching you that they really need to upgrade their skills.
jon_darkstar is right when it comes to improving the logic, however if you want to see how GO TO works here goes:
IF FIRST < SECOND
MOVE FIRST TO WS
GO TO C10-RESULT.
END-IF.
MOVE SECOND TO WS.
C10-RESULT.
MOVE WS TO RESULT.
C10-RESULT. starts a paragraph and has to be a unique name in your code SECTION. By convention it should also start with the same prefix as the enclosing section. Therefore this example assumes that your code SECTION is something like C00-MAIN-PROCESS SECTION.
A new non-Answer has brought this silly question to light.
ELSE in the IF is the 100% obvious answer. It is deeply odd that GO TO has to be used whereas ELSE may not be used.
Another way, surprised it didn't come up:
MOVE SECOND TO WS
IF FIRST LESS THAN SECOND
MOVE FIRST TO WS
END-IF
MOVE WS TO RESULT
No ELSE, no GO TO. Extra MOVE executed when FIRST is less than second, though.
To include a GO TO is simple, but stupid. Add a GO TO. A GO TO has to go somewhere (unless using ALTER ... TO PROCEED TO ..., which everyone hopes you weren't), so make a label at the point you want it to arrive, and add the name of that label to the GO TO.
A label is a user-defined word. If referenced (as in this case) it must be unique within a SECTION, if you use SECTIONs, which you don't need to, otherwise unique within the program and whether referenced or not it may not be the same name as something else (like a data-definition or the internal name of a file).
A label is a procedure-name. A procedure-name should terminate with a period/full-stop and the procedure itself should also terminate with a period/full-stop.
What about the MOVE FUNCTION MIN ( ... ) ... as a solution?
Well, it works. If other staff at your site are not used to it, you will not be thanked for using it (without prior discussion, anyway).
What does it do? Well, in Enterprise COBOL, the compiler generates an extra little area, copies the first argument to that area, tests against the second argument, copies the copy of the first argument, or the second argument, whichever is relevant, to the result.
Vs the ELSE, that is an extra storage area defined, an extra instruction for addressability of that, and an extra Assembler move (MVC) plus the lack of ready recognition.
Better for programmers new to COBOL, used to a multitude of functions in other languages? Not really, as they will be soundly beaten if they don't write programs that can be understood (at 2am) by the rest of the staff.
IF FUNCTION MIN(VAR1 VAR2 VAR3 VAR4 VAR5) = 17
It's another downside of FUNCTION. You see, you can do that. Then, at 2am, when the program has crashed 32 lines later, after VAR1 and VAR3 have been changed, are you going to be able to find the result of that IF in the core dump? Maybe, maybe not. Depends if any other functions, and of what type, have been used. At 2am, you don't want that. Not at all.
On the upside, it is less typing. For those who type, rather than use the editor.
In our shop, we'd use the example provided by Bill Woodger. However, we do use periods as scope-terminators. COBOL should be structured and use the KISS principle, just like any other language. This:
MOVE SECOND TO WS.
IF FIRST LESS THAN SECOND
MOVE FIRST TO WS.
MOVE WS TO RESULT.
Note that this only works if we are assured that SECOND and FIRST have numeric values, or that WS is a PIC X() string, not a numeric PIC 9().
This is by far the easiest to read. No ELSE or GO TO required.
I've got a massive script with about 20 embedded if statements (Yay!) that is used to parse through a data file. And in a sense, that's correct because the script should not continue operating if any of those evaluations fail.
But my gut says there's a more elegant way to accomplish the same thing. I'm familiar with the statemachine plugin for rails, but that seems to be overkill (it seems to be overkill).
Any chance there's a slightly more elegant way to reduce the number of embedded 'ifs' either through a workflow, or some other way?
reverse the conditions of the if statements and leave the particular function(if you can). This way you get a lot of if's behind each other instead of nested
This is mostly code specific, but I can suggest 2 ways:
case .. when .. then .. structure.
Effectively using send or eval methods.
One approach is to construct a hash or array in which the contents are Procs that each encapsulate a given conditional. Then you can loop through the procs and test your data against each one.
Just refactor the code and split parts of the conditional sections out to different functions. It will not reduce the nested if deepths but make it more readable.
Otherwise there is very little to say as it is a very generic question.
Use haml :P
(so you dont need to end the if tags..)