Octave vectorize strsplit return value into separate variables - octave

I have a file with a list of records which I parse one line at a time. Each record is newline delimited and each value is space delimited. This is just a simplified example, but it has a similar structure to the real data.
Bob blue pizza
Sally red sushi
The first value is a name, then their favorite color, then their favorite food. Let's say this is in a processing loop and I want to set variables up for each value. For the first line, my values should look like this.
friendsName = "Bob";
favoriteColor = "blue";
favoriteFood = "pizza";
I read in the line and start out with
lineInFile = "Bob blue pizza";
strsplit seems like a good idea, but it outputs a cell array instead of a matrix of strings and I end up with
strsplit(lineInFile, " ") =
{
[1,1] = Bob
[1,2] = blue
[1,3] = pizza
}
I want something like
{friendsName,favoriteColor,favoriteFood} = strsplit(lineInFile, " ");
This gives me error: invalid lvalue function called in expression
Arrays can be used as lvalues, so I tried
cell2mat(strsplit(lineInFile, " "))
ans = Bobbluepizza
That's not what I want.

This worked.
[friendsName favoriteColor favoriteFood] = strsplit(lineInFile, " "){1,:}

Related

IIf query decimal removal

Trying to attempt the following in MS Access.
Convert data in one field to an 18 digit number starting with 01 in another field.
There are also some conditions that have to be met:
the first dash should become double zeros
the second dash should be removed
the third and fourth dash should be a single zero
the decimal must also be replaced with a zero
My query works fine until the decimal is the 15th character in the data.
Here is the query:
SELECT MasterVacant.ParcelIdNumber,
"01" + Mid([ParcelIdNumber],1,2) + "00" + Mid([ParcelIdNumber],4,2) + Mid([ParcelIdNumber],7,1)
+ IIf(Mid([ParcelIDNumber],11,1) = "", "0"+Mid([ParcelIDNumber],9,2), Mid([ParcelIDNumber],9,3))
+ IIf(Mid([ParcelIDNumber],14,1) = ".", "0"+Mid([ParcelIDNumber],12,2), Mid([ParcelIDNumber],12,3))
+ Mid([ParcelIDNumber],15,3) AS ParcelNumber
FROM MasterVacant;
Here is a start and finish example...
'12-06-1-00-50.000-RR' should become '011200061000050000'
'12-06-3-07-09.000-RR' should become '011200063007009000'
'13-35-1-01-129.000-RR' should become '011300035100112900'
However, instead of getting `0113000351001129000' I get '013000351001129.00'.
The issue is how do I remove the decimal when the decimal is the 15th character like in the third set of example?
I receive the data as a single column. Some of it is below....
1. 13-35-1-07-29.000-RR
2. 13-35-1-01-112.000-RR (Removing the decimal when the data is like this is the issue)
3. 13-35-4-01-01.000-RR
4. 13-35-4-02-04.000-RR
5. 13-35-1-13-17.000-RR
The output for the above data should be
1. 011300351007029000
2. 011300351001112000
3. 011300354001001000
4. 011300354002004000
5. 011300351013017000
Use a custom function:
Public Function Make18(ByVal Value As String) As String
Const Head As String = "01"
Const Tail As String = "000"
Const Lead As String = "00"
Dim Parts As Variant
Dim Part As Integer
Dim Result As String
Parts = Split(Split(Value, ".")(0), "-")
For Part = LBound(Parts) To UBound(Parts)
Select Case Part
Case 0
Parts(Part) = Head & Parts(Part)
Case 1
Parts(Part) = Lead & Parts(Part)
Case 3, 4
Parts(Part) = Right(Lead & Parts(Part), 3)
End Select
Next
Result = Join(Parts, "") & Tail
Make18 = Result
End Function
and your query becomes:
SELECT
MasterVacant.ParcelIdNumber,
Make18([ParcelIdNumber]) AS ParcelNumber
FROM
MasterVacant;
I am assuming you meant the opposite where:
12-06-1-00-50.000-RR should become 011200061000050000
12-06-3-07-09.000-RR should become 011200063007009000
13-35-1-01-129.000-RR should become 0113000351001129.00
I would recommend the REPLACE() in MSACCESS to strip the dashes out. Once you have the dashes out you can MID()
Unfortunately your attempted code does something different with the 3rd row because 3 zeros are being put in when there should be only two in my opinion.
Try in a text box:
=Replace("13-35-1-01-129.000-RR","-","")
will return 1335101129.000RR
and see if that assists you in making your code.
Maybe go one step further and put it in a function.

When appending to a List of JSON Objects in python, why is it duplicating only the "2nd layer" objects?

Here is my code.
def generateNewDevices(numofdevices):
global simulated_devices
for x in range(numofdevices):
new_device = reference_device.copy()
new_device["accel"]["accx"] = random.randint(-32768, 32767)
new_device["accel"]["accy"] = random.randint(-32768, 32767)
new_device["accel"]["accz"] = random.randint(-32768, 32767)
new_device["location"]["gpsla"] = random.uniform(MINLAT, MAXLAT)
new_device["location"]["gpslo"] = random.uniform(MINLON, MAXLON)
new_device["temp"] = random.randint(-127, 127)
new_device["status"] = random.randint(0, 1)
str1 = new_device["deviceName"]
str1 = str1[:-3]
str2 = str(x).zfill(3)
str1 += str2
new_device["deviceName"] = str1
node_red_send(URL, new_device)
print(new_device)
simulated_devices.append(new_device)
generateNewDevices(3)
for x in range(len(simulated_devices)):
print(simulated_devices[x])
Why when printing through the list of values at the end, does the list show the "new device" data for appended JSON objects "1 layer deep" (temp, status and name) but duplicate the data for "2 layers deep" (accx, accy, gpsla)?
The .copy()s are in there because I was having issues with python append duplicating all the values at first. Is this some variation of the same issue? I even tried .copy()ing right before appending to the list. (I come from a c/c++ background so I do not fully understand why python does some of its things)
Any help appreciated.
Kr, apuri123.
I doubt anyone will end up here when searching for an answer, but in case you do, you are looking for "deepcopy":
import copy
original = {} #object with as many objects within objects as you want
myCopy = copy.deepcopy(original)
Google "python deepcopy" and you should be able to find what you are looking for.

Octave - putting words into vector

I am working on creating an email filter. I have a sample email which says something like this:
Hi how are you lets meet up
I want to put each one of these words into a vector. I am looking for something like this.
Words = ['Hi';'how','are','you','lets','meet','up']
and when I enter
words(1), I want it to display Hi.
I really don't know where to start. I found answers for different languages such as Ruby and JS. But not for Octave.
Adding to Andy's answer about cells, you can collect your email as a string and process it using string operations such as strtok, strsplit etc. e.g.
octave:7> s = 'Hi how are you lets meet up';
octave:8> words = strsplit(s, ' ')
words =
{
[1,1] = Hi
[1,2] = how
[1,3] = are
[1,4] = you
[1,5] = lets
[1,6] = meet
[1,7] = up
}
octave:9> words{1}
ans = Hi
Use Cell Arrays of Strings:
octave:1> words = {'hi', 'how', 'are', 'you', 'lets', 'meet', 'up'};
octave:2> words{1}
ans = hi
and you can use indexing:
octave:4> words{3:4}
ans = are
ans = you
if you struggle why this returns a different result:
octave:5> words(3:4)
ans =
{
[1,1] = are
[1,2] = you
}
then read here:
So with ‘{}’ you access elements of a cell array, while with ‘()’ you access a sub array of a cell array.

Calling out the Sum of a Data I Made

I am working with a text file and need to call out the sum found from my last column of data [4] that I have made. I have done everything I need for the last column and have used total += square to add the first value in row one with the next value in row two and so on till I hit my 100th row in my text file. Now I need to be able to take my sum that I want in my 100 row and store it as a variable. How can I go about calling it out?
fullPath = open("localzscoretest.txt", "r") #Where I have our the current table located
import math
def globalchiSquare(fullPath):
for line in fullPath:
line = line.strip() #Strip it
lines = line.split(',') #split it
rows = lines[1:] #keeping the numbers
rows = map(float, rows) #getting my numbers in the .txt ready for the equation
square = (rows[4]**2) #squared the z score column
total += square
print total
globalchiSquare(fullPath)
change
square = (rows[4]**2) #squared the z score column
to be
square += (rows[4]**2) #squared the z score column
Give globalchiSquare a readlines() method in order to iterate.
In the function do
def globalchiSquare(fullPath):
for line in fullPath.readlines():
. . .
You should also keep your variables clear. When you say lines, it seems like you are saying that there are multiple--rows, too.
Just make it more simple and include the sum.
def globalchiSquare(fullPath):
total = 0
for line in fullPath.readlines(): # readlines() method
line = line.strip() # cut off ends
line = line.split(',') # create list
row = line[1:] # create row from line
row = map(float,row) # convert to floats
square = row[4]**2 # find square
print 'square',square
total += square
print 'total',total
return total
my_var = globalchiSquare(fullPath)
print my_var # should give total
EDIT: The return statement allows you to store the value of total.

Adobe After Effects: Keep "Expression-Relations" when duplicating multiple layers

just wanted to ask, whether there is a way to keep the relations of expressions going when duplicating layers.
E.g. I have two layers, "LayerA" and "LayerB". Now I have an expression going on in "LayerB" saying, that its position always equals the position of "LayerA".
Now when I duplicate those two and get "LayerA 2" and "LayerB 2" I want the expression in "LayerB 2" to reference to "LayerA 2"'s position rather than "LayerA"'s position!
While it is no problem to simply change the expression when there is only one of them, it gets quite hard when you have multiple expressions going on ...
You might end up wanting to organize your comp differently, but, given your example (and exactly those name lengths), this position expression will work to find the appropriate 'target layer':
//base name to work from:
baseName = "Layer";
//length of that:
nameLen = baseName.length;
//this layer's name:
myName = thisLayer.name;
if (myName.length == nameLen) {
//if they are the same, then it is the original
// (non-duplicated) version
thisComp.layer("LayerA").transform.position;
} else {
//get tail string, the space and number:
tailStr = myName.substring(nameLen+1, myName.length);
//build new target layer name with "A":
targetName = myName.substring(0, (nameLen)) + "A" + tailStr
//new line pointing to target layer:
thisComp.layer(targetName).transform.position;
}