How to extract data from .txt table with a for loop - python-3.x

I want to open Learn_full_data.txt extract some rows from it and write them on a new file called All_Data.txt using a foor loop.
Learn_full_data.txt Table:
vp run trial img_order mimg perc_aha_norm perc_gen_norm moon_onset moon_pulse moon_pulse_time answer_time answer_pulse answer_pulse_time fix_time fix_pulse fixpulse_time flash_onset flash_pulse flash_pulse_time_(flash_onset) tar_time_(greyscale) tar_pulse tarpulse_time answer RT_answer aha RT_aha condition solved_testphase RT_solvedtest oldnew RT_oldnew remknow RT_remknow
1 1 1 70 mimg433 0,4375 0,5625 18066 6 20029 20083 7 22029 22099 8 24029 24116 8 24029 24633 10 28029 nicht_erkannt 1055 Aha 1145 exp 0 0 old 2030 know 381
1 1 2 146 mimg665 0,6 0,4 30666 12 32029 32683 13 34029 34699 16 40028 40716 16 40028 41233 18 44028 erkannt 990 keinAha 1240 exp 1 2758 old 634 rem 1063
2 1 1 130 mimg640 0,666667 1 17366 5 19328 19383 6 21328 21399 8 25328 25416 8 25328 25933 10 29328 erkannt 871 keinAha 2121 base 1 2891 old 3105 know 533
2 1 2 83 mimg500 0,454545 0,272727 33966 13 35328 35983 14 37328 37999 15 39328 40016 15 39328 40533 17 43328 nicht_erkannt 1031 Aha 1153 exp 0 0 new 2358 kA 2358
The row Vp has two subjects, so I created a list with the subjects from the row Vp (there are many more, but I've just pasted an excerpt from it):
list = ['1','2']
Now I want to iterate over the list with this code (if the item in the list is the same as Vp, than write on All_Data.txt some rows from Learn_full_data.txt):
Learn = open('Learn_full_data.txt','r')
file = open('All_Data.txt','w')
file.write('Vp\tImg\tDescription\tPerc_gen_norm\tPerc_aha_norm\tCond\tGen\tRt_Gen\tRt_Solved\tInsight\tRt_Insight\tOldNew\tRt_OldNew\tRemKnow\tRt_RemKnow\n')
for i in list:
for splitted in Learn:
splitted = splitted.split()
Vp = splitted[0]
Img = str(splitted[4])
Perc_gen_norm = splitted[6]
Perc_aha_norm = splitted[5]
Cond = splitted[26]
Gen = splitted[22]
Rt_Gen = splitted[23]
Insight = splitted[24]
Rt_Insight = splitted[25]
Rt_Solved = splitted[28]
OldNew = splitted[29]
Rt_OldNew = splitted[30]
RemKnow = splitted[31]
Rt_Remknow = splitted[32]
if i == str(Vp):
file.write(str(Vp)+'\t'+str(Img)+'\t'+'Description'+'\t'+str(Perc_gen_norm)+'\t'+str(Perc_aha_norm)+'\t'+str(Cond)+'\t'+str(Gen)+'\t'+str(Rt_Gen)+'\t'+str(Insight)+'\t'+str(Rt_Insight)+'\t'+str(Rt_Solved)+'\t'+str(OldNew)+'\t'+str(Rt_OldNew)+'\t'+str(RemKnow)+'\t'+str(Rt_Remknow)+'\n’)
The Code output is just the first iteration from the list. I was expecting it to continue iterating:
Vp Img Description Perc_gen_norm Perc_aha_norm Cond Gen Rt_Gen Rt_Solved Insight Rt_Insight OldNew Rt_OldNew RemKnow Rt_RemKnow
1 mimg433 Description 0,5625 0,4375 exp nicht_erkannt 1055 Aha 1145 0 old 2030 know 381
1 mimg665 Description 0,4 0,6 exp erkannt 990 keinAha 1240 2758 old 634 rem 1063
The second iteration designated on the list doesn't happen. The second item of the list is '2' and the Vp item is also '2', so the second iteration should return the same for Vp '2' as it did for Vp '1'. Why does the for loop stop in Vp '1'?

The problem is that you iterate through all the lines in your code in the first iteration of your for i in list loop. In the second iteration, e.g. i = 2, the read cursor is still at the end of the file. You have to set it to the first line in each iteration. This can be done with Learn.seek(0):
for i in list:
Learn.seek(0)
for splitted in Learn:
splitted = splitted.split('\t')
Vp = splitted[0]
Img = str(splitted[4])
Perc_gen_norm = splitted[6]
Perc_aha_norm = splitted[5]
Cond = splitted[26]
Gen = splitted[22]
Rt_Gen = splitted[23]
Insight = splitted[24]
Rt_Insight = splitted[25]
Rt_Solved = splitted[28]
OldNew = splitted[29]
Rt_OldNew = splitted[30]
RemKnow = splitted[31]
Rt_Remknow = splitted[32]
if i == str(Vp):
file.write(str(Vp)+'\t'+str(Img)+'\t'+'Description'+'\t'+str(Perc_gen_norm)+'\t'+str(Perc_aha_norm)+'\t'+str(Cond)+'\t'+str(Gen)+'\t'+str(Rt_Gen)+'\t'+str(Insight)+'\t'+str(Rt_Insight)+'\t'+str(Rt_Solved)+'\t'+str(OldNew)+'\t'+str(Rt_OldNew)+'\t'+str(RemKnow)+'\t'+str(Rt_Remknow))

Related

mgcv::gam, Error in names(dat) <- object$term : attribut 'names' [2] as to be same length as vector [1]

I want to run a hieratchical GAM in the mgcv package using the gam function. I used the same form of model in brms without problem and I will eventually re-run the same model in brms, but the deadline for an abstract submission in Sunday so I want to try the model in mgcv to have quicker results.
My formula:
f = MDS1 ~ 1 + exposed + s(YEAR,bs = "tp")+ s(LEVEL, bs = "tp") +
t2(YEAR, SITE, bs = c("tp","re")) + s(INTERTIDAL_TRANSECT, bs = "re",
m = 1)
My data:
Classes ‘data.table’ and 'data.frame': 3992 obs. of 9 variables:
$ unique_id : chr "Babb's Cove-1-0-1988" "Babb's Cove-1-0-1989" "Babb's Cove-1-0-1990" "Babb's Cove-1-0-1992" ...
$ MDS1 : num -0.607 -0.607 -0.607 -0.607 -0.607 ...
$ MDS2 : num 0.19 0.19 0.19 0.19 0.19 ...
$ MDS3 : num 0.36 0.36 0.36 0.36 0.36 ...
$ SITE : chr "Babb's Cove" "Babb's Cove" "Babb's Cove" "Babb's Cove" ...
$ INTERTIDAL_TRANSECT: Factor w/ 21 levels "1","2","5","7",..: 1 1 1 1 1 1 1 1 1 1 ...
$ LEVEL : num 0 0 0 0 0 0 0 1 1 1 ...
$ YEAR : num 1988 1989 1990 1992 1994 ...
$ exposed : Factor w/ 2 levels "1","2": 2 2 2 2 2 2 2 2 2 2 ...
- attr(*, ".internal.selfref")=<externalptr>
- attr(*, "sorted")= chr "unique_id"
I have 2 questions:
a)
When I try to fit the model with fit_count <- gam(f, data = count_merge, method = "REML", family = gaussian()) I get :
Error in names(dat) <- object$term :
attribut 'names' [2] doit être de même longueur que le vecteur [1]
I think it's something with the t2() argument of the formula.
b)
I usually run GAM with brms and my formula for that model was :
MDS1 ~ 1 + exposed + s(YEAR,bs = "tp")+ s(LEVEL, bs = "tp") + t2(YEAR, SITE, bs = c("tp","re"), full = T) +(1|r|INTERTIDAL_TRANSECT),
family = gaussian()
Is my way to adapt the formula to mgcv::gam OK?
Q a)
Your SITE vector is a character vector and it is required to be a factor.
Q b)
That looks OK, but you don't need the m = 1 in the s(INTERTIDAL_TRANSECT, bs = "re") term.
You should also use the full = TRUE option on the t2() term if you want the parameterisation to be the same between your {brms} call the {mgcv} one.

MDP Policy Plot for a Maze

I have a 5x-5 maze specified as follows.
r = [1 0 1 1 1
1 1 1 0 1
0 1 0 0 1
1 1 1 0 1
1 0 1 0 1];
Where 1's are the paths and 0's are the walls.
Assume I have a function foo(policy_vector, r) that maps the elements of the policy vector to the elements in r. For example 1=UP, 2=Right, 3=Down, 4=Left. The MDP is set up such that the wall states are never realized so policies for those states are ignored in the plot.
policy_vector' = [3 2 2 2 3 2 2 1 2 3 1 1 1 2 3 2 1 4 2 3 1 1 1 2 2]
symbols' = [v > > > v > > ^ > v ^ ^ ^ > v > ^ < > v ^ ^ ^ > >]
I am trying to display my policy decision for a Markov Decision Process in the context of solving a maze. How would I plot something that looks like this? Matlab is preferable but Python is fine.
Even if some body could show me how to make a plot like this I would be able to figure it out from there.
function[] = policy_plot(policy,r)
[row,col] = size(r);
symbols = {'^', '>', 'v', '<'};
policy_symbolic = get_policy_symbols(policy, symbols);
figure()
hold on
axis([0, row, 0, col])
grid on
cnt = 1;
fill([0,0,col,col],[row,0,0,row],'k')
for rr = row:-1:1
for cc = 1:col
if r(row+1 - rr,cc) ~= 0 && ~(row == row+1 - rr && col == cc)
fill([cc-1,cc-1,cc,cc],[rr,rr-1,rr-1,rr],'g')
text(cc - 0.55,rr - 0.5,policy_symbolic{cnt})
end
cnt = cnt + 1;
end
end
fill([cc-1,cc-1,cc,cc],[rr,rr-1,rr-1,rr],'b')
text(cc - 0.70,rr - 0.5,'Goal')
function [policy_symbolic] = get_policy_symbols(policy, symbols)
policy_symbolic = cell(size(policy));
for ii = 1:length(policy)
policy_symbolic{ii} = symbols{policy(ii)};
end

How to loop values of a variable through a nested while loop calling on a function in Python

I have a while loop that calls on a function (def update(i)) and performs the calculation for the required number of times (until the while loop condition is no longer met) in Python3. What I now want to do is put different values of 'i' through the while loop and therefore through the equation 'dv' (shown below). So when the while loop ends I need the whole process to repeat with the next 'i' value. All the i values are in an np.arange array called 'i_es'. I have tried to implement this with the while loop nested inside a for loop as shown below...
import numpy as np
def update(i) :
dv = (e_l - v_s[-1] + i*r_m)/tau_m
v_s.append(v_s[-1] + (dv*dt))
return is_spiked()
def is_spiked() :
if v_s[-1] > v_th:
v_s[-1] = v_r
return True
return False
r_m = 10
tau_m = 10
v_th = -40
e_l = -70
v_r = -70
v_s = [v_r]
spike_count = 0
t = 0
t_total = 1000
dt = 1
i_e_start = 4
i_e_step = 0.1
i_e_final = 5
i_es = np.arange(i_e_start,i_e_final+i_e_step,i_e_step)
for i in i_es :
while t < t_total :
if update(i) :
spike_count += 1
t += dt
print ("Current = ",+ i, " Spike count = ", + spike_count)
However, when I run this I get the following output:
Current = 4.0 Spike count = 71
Current = 4.1 Spike count = 71
Current = 4.2 Spike count = 71
Current = 4.3 Spike count = 71
Current = 4.4 Spike count = 71
Current = 4.5 Spike count = 71
Current = 4.6 Spike count = 71
Current = 4.7 Spike count = 71
Current = 4.8 Spike count = 71
Current = 4.9 Spike count = 71
Current = 5.0 Spike count = 71
I can see that the current ('i') values are increasing as they should each time but the spike count is not changing.. The answer is always from the first value ('i' = 4) run through the loop.
Can anyone help with this?
Thanks in advance.

Replace a string in a text file

I'd like to replace a string in a text file in MATLAB.
To read the specified line I used the code :
fid = fopen(file_name, 'r');
tt = textscan(fid, '%s', 1, 'delimiter', '\n', 'headerlines', i);
ttt = str2num(tt{1}{1});
where file_name is the name of my file and ttt is a cell array that contains the i-th string converted in integer.
For example, ttt = 1 2 3 4 5 6 7 8
Now, I'd like to change ttt with ttt = 0 0 0 0 0 0 0 0
and write the new ttt at the i-th line in the file.
Does anybody have an idea to handle this?
A possible implementation is
fid = fopen('input.txt', 'r+');
tt = textscan(fid, '%s', 1, 'delimiter', '\n', 'headerlines', 1); % scan the second line
tt = tt{1}{1};
ttt = str2num(tt); %parse all the integers from the string
ttt = ttt*0; %set all integers to zero
fseek(fid, length(tt), 'bof'); %go back to the start of the parsed line
format = repmat('%d ', 1, length(ttt));
format = format(1:end-1); %remove the trailing space
fprintf(fid, format, ttt); %overwrite the text in the file
fclose(fid); %close the file
This will change the input.txt from:
your first line
1 2 3 4 5 6 7 8
5 5 5 5 5 5 5 5
into
your first line
0 0 0 0 0 0 0 0
5 5 5 5 5 5 5 5
Note that it is only possible to overwrite existing characters in the file. If you want to insert new characters, you have two rewrite the full file or at least from the position where you want to insert your new characters.
Or use something like this ...
fid = fopen('input_file.txt', 'r');
f = fread(fid, '*char')';
fclose(fid);
f = strrep(f, ' ', ''); % to remove
f = strrep(f, ' ', ' .'); % to replace
% save into new txt file
fid = fopen('output_file.txt', 'w');
fprintf(fid, '%s', f);
fclose(fid);

Read measurement data from a text file and put them in an array in Fortran

I would like to read my measurement data from a text file. The data have e.g. following form:
0 0.0531139
0.000157095 0.306123
0.000314191 0.133868
0.000471286 0.29799
0.000628381 0.0182098
0.000785477 0.121222
0.000942572 0.32111
0.00109967 0.0267326
0.00125676 0.49554
0.00141386 0.433729
My code is as follows:
SUBROUTINE test(name)
implicit none
character :: name*(*)
real*8,allocatable, dimension(:,:) :: measMatrix
integer :: i,
& nrcols
nrcols = 2
nrrows = 10
allocate(measMatrix(nrcols,nrrows))
open(unit = 20, file = Dateiname, status = 'old', action = 'read')
do i = 1, nrrows
read(20,*) measMatrix(i,1:nrcols)
end do
close(20)
open(unit = 10, file = 'Test4.txt')
do i = 1,nrrows
write(10,777) (measMatrix(i,j), j = 1,nrcols)
end do
close(10)
777 format(F12.9,4X,F12.9)
deallocate(measMatrix)
END
However, the output is wrong:
0.000000000 0.000314191
0.000157095 0.000471286
0.000314191 0.000628381
0.000471286 0.000785477
0.000628381 0.000942572
0.000785477 0.001099670
0.000942572 0.001256760
0.001099670 0.001413860
0.001256760 0.495540000
0.001413860 0.433729000
What am I doing wrong ? :(
Thanks in advance for the help.
The first dimension is the fasted changing one, and the one contiguous in memory.
So in memory space your (10,2) is laid out as:
1 11
2 12
3 13
4 14
5 15
6 16
7 17
8 18
9 19
10 20
Maybe you want this:
nrrows = 10
nrcols = 2
allocate(measMatrix(10,2))
do i = 1, nrrows
read(20,*) measMatrix(i,:)
end do
...
do i = 1, nrrows
write(10,777) measMatrix(i,:)
end do
I prefer this:
integer :: Crnt_Row, Crnt_Col
nrrows = 10
nrcols = 2
allocate(measMatrix(10,2))
WRITE(*,*)'Shape(measMatrix)=',SHAPE(measMatrix)
do CurrRow = 1, nrrows
read(20,*) measMatrix(CurrRow,:)
end do
...
do CurrRow = 1, nrrows
write(10,777) measMatrix(CurrRow,:)
end do
Using IMPLICIT NONE will also help along the lines of what #d_1999 mentioned.

Resources