PHPExcel formulas goes a mess - phpexcel

Following code removes three rows at the top and saves xls to new file. But all formulas are destroyed. I need to remove three rows and all columns after D and keep formula values in columns C and D. C and D column formulas comes from E and F columns. But because E and F is removed, it will mess up C and D. How to fix this?
<?php
error_reporting(E_ALL & ~E_STRICT & ~E_NOTICE);
require_once('PHPExcel/Classes/PHPExcel.php');
$reader = PHPExcel_IOFactory::createReader('Excel5');
$reader->setReadDataOnly(true);
set_include_path(get_include_path() . PATH_SEPARATOR . 'Classes/');
/** PHPExcel_IOFactory */
include 'PHPExcel/IOFactory.php';
//Defining File Type
$fileType = "Excel5";
//Retrieving File
$tmpfname = "tasoituslista.xls";
$tmpfname2 = "tasoituslista2.xls";
//Loading file into PHPExcel
$objPHPExcel = PHPExcel_IOFactory::load($tmpfname);
$worksheet = $objPHPExcel->getSheet(0); //Worksheet of file defined as first
$lastRow = $worksheet->getHighestRow();
$objPHPExcel->getActiveSheet()->removeRow(1, 3);
//Write file into original file
$objWriter = PHPExcel_IOFactory::createWriter($objPHPExcel, $fileType);
$objWriter->save($tmpfname2);
?>

Clearly, if a formula use data from cells that are being removed, it will break the formula.
You have a couple of options.
Don't remove columns E and F, but hide them.... the formula will still work, but the values it uses will be hidden
Before you remove columns E and F, get the calculated values for your formula cells, and update the formula cells with that value, so it isn't a formula cell anymore, but contains the actual value

Related

ndgrid - input and output from cell array

I am converting some code from Matlab to Scilab and ran into trouble trying to use Scilab 'ndgrid' function with input and output from cell array.
Specifically, I use ndgrid with an a priori unknown number of vectors (contained in a cell array) and intend to get the output grid matrices in a cell array.
In Matlab the code looks like that:
v = {0:3,0:3}; // not necessarily of length 2 (dynamically set)
G = cell(1,2);
[G{:}] = ndgrid(v{:});
I can't obtain similar behaviour using Scilab (neither for the input, nor for the output).
For the input, Scilab returns ndgrid: Wrong type for argument #1: Booleans, Integers, Decimals, Complexes, Polynomials, Rationals or Texts expected.
I hope a workaround exists. Thanks for your help!
v = list(0:3, 0:2); // not necessarily of length 2 (dynamically set)
G = list();
c = strcat(msprintf("G(%i)\n",(1:length(v))'),",")
execstr("[" + c + "] = ndgrid(v(:))")
G
does it:
--> c = strcat(msprintf("G(%i)\n",(1:length(v))'),",")
c =
"G(1),G(2)"
--> execstr("[" + c + "] = ndgrid(v(:))")
--> G
G =
(1) : [4x3 constant]
(2) : [4x3 constant]

Preallocating a dict of dicts

When I run #code_warntype on the following function (Shown in bold are the expressions that are likely raising the red flags.)
function cardata(df::DataFrame,Emission_val::Float64,search_cars::Dict{String,Tuple{Int64,Int64}}=Dict("Car1" => (1000,10000), "Car2" => (1000,50000), "Car3" => (1000,6000)),
all_cars::Array{String,1}=["Car1","Car2","Car3","Car4","Car5","Car6"])
**species = Dict()**
# The data file containing car information of interest
car_library = joinpath(path,"cars.csv")
df_car_data=CSV.read(car_library,header=["Model","Velocity","Emission_Value","Mass","Column6"],delim='\t')
#delete unused column
deletecols!(df_car_data, :Column6)
#create a new column with only the car Identifier name
df_car_data[:Identifier_car]=[split(i,r"[0-9]+")[1] for i in df_car_data[:Model]]
#get the properties of all_cars from the cars_data table
for search_models in all_cars
**cars[search_models] = Dict()**
for i in 1:1:length(df_cars_data[1])
num = split(df_cars_data[:Model][i],r"[0-9]+")[1]
alpha = split(df_cars_data[:Model][i],r"[a-zA-Z]+")[2]
if ( num == search_models )
species[num][alpha] = df_car_data[:Velocity][i]
end
end
end
end
I get the following warning highlighted in red:
Body::Tuple{Dict{Any,Any},Union{DataFrame,DataFrameRow{DataFrame,Index}},Any,Any}.
How to preallocate the types for dicts in such a case, assuming that I know the length of data that will populate the dict?
You have not provided a minimal working example.
Have a look at the code below. Note that for efficiency reasons
it is recommended to use Symbol a the key rather than String
species = Dict{Symbol,Dict{Symbol,Float64}}()
group = get!(()->Dict{Symbol,Float64}(),species,Symbol("audi"))
group[Symbol("a4")]=10.5
group[Symbol("a6")]=9.5
And now printing the output:
julia> println(species)
Dict(:audi=>Dict(:a6=>9.5,:a4=>10.5))

Copy a huge file with Julia Mmap

I have a big file (75GB) memory mapped in an array d that I want to copy in another m. Because I do not have 75GB of RAM available, I did:
for (i,v) in enumerate(d)
m[i] = v
end
In order to copy the file value after value. But I get a copy rate of ~2MB/s on a SSD where I expect at least 50MB/s both in read and write.
How could I optimize this copy rate?
=== [edit] ===
According to the comments, I changed my code to the following, which sped up the write rate to 15MB/s
function copydcimg(m::Array{UInt16,4}, d::Dcimg)
m .= d
Mmap.sync!(m)
end
copydcimg(m,d)
At this point, I think I should optimize the Dcimg code. This binary file is made of frames spaced by a timestamp. Here is the code I use to access the frames:
module dcimg
using Mmap
using TOML
struct Dcimg <: AbstractArray{UInt16,4} # struct allowing to access dcimg file
filename::String # filename of the dcimg
header::Int # header size in bytes
clock::Int # clock size in bytes
x::Int
y::Int
z::Int
t::Int
m # linear memory map
Dcimg(filename, header, clock, x, y, z, t) =
new(filename, header, clock, x, y, z, t,
Mmap.mmap(open(filename), Array{UInt16, 3},
(x*y+clock÷sizeof(UInt16), z, t), header)
)
end
# following functions allows to access DCIMG like an Array
Base.size(D::Dcimg) = (D.x, D.y, D.z, D.t)
# skip clock
Base.getindex(D::Dcimg, i::Int) =
D.m[i + (i ÷ (D.x*D.y))*D.clock÷sizeof(UInt16)]
Base.getindex(D::Dcimg, x::Int, y::Int, z::Int, t::Int) =
D[x + D.x*((y-1) + D.y*((z-1) + D.z*(t-1)))]
# allowing to automatically parse size
function Dcimg(pathtag)
p = TOML.parsefile(pathtag * ".toml")
return Dcimg(pathtag * ".dcimg",
# ...
)
end
export Dcimg, getframe
end
I got it! The solution was to copy the file chunk by chunk lets say by frame (around 1024×720 UInt16). This way I reached 300MB/s, which I didn't even know was possible in single thread. Here is the code.
In module dcimg, I added the methods to access the file frame by frame
# get frame number n (starting form 1)
getframe(D::Dcimg,n::Int) =
reshape(D.m[
D.x*D.y*(n-1)+1 + (n-1)*D.clock÷sizeof(UInt16) : # cosmetic line break
D.x*D.y*n + (n-1)*D.clock÷sizeof(UInt16)
], D.x, D.y)
# get frame for layer z, time t (starting from 1)
getframe(D::Dcimg,z::Int,t::Int) =
getframe(D::Dcimg,(z-1)+D.z*(t-1))
Iterating over the frames within a loop
function copyframes(m::Array{UInt16,4}, d::Dcimg)
N = d.z*d.t
F = d.x*d.y
for i in 1:N
m[(i-1)*F+1:i*F] = getframe(d, i)
end
end
copyframes(m,d)
Thanks all in comments for leading me to this.
===== edit =====
for further reading, you might look at:
dd: How to calculate optimal blocksize?
http://blog.tdg5.com/tuning-dd-block-size/
which give hints about the optimal block size to copy at a time.

scilab submatrix incorrectly defined

I am stuck at creating a matrix of a matrix (vector in this case)
What I have so far
index = zeros(size(A)) // This is some matrix but isn't important to the question
indexIndex = 1;
for rows=1:length(R)
for columns=1:length(K)
if(A(rows,columns)==x)
V=[rows columns]; // I create a vector holding the row + column
index(indexIndex) = V(1,2) // I want to store all these vectors
indexIndex = indexIndex + 1
end
end
end
I have tried various ways of getting the information out of V (such as V(1:2)) but nothing seems to work correctly.
In other words, I'm trying to get an array of points.
Thanks in advance
I do not understand your question exactly. What is the size of A? What is x, K and R? But under some assumptions,
Using list
You could use a list
// Create some matrix A
A = zeros(8,8)
//initialize the list
index = list();
// Get the dimensions of A
rows = size(A,1);
cols = size(A,2);
x = 0;
for row=1:rows
for col=1:cols
if(A(row,col)==x)
// Create a vector holding row and col
V=[row col];
// Append it to list using $ (last index) + 1
index($+1) = V
end
end
end
Single indexed matrices
Another approach would be to make use of the fact an multi-dimensional matrix can also be indexed by a single value.
For instance create a random matrix named a:
-->a = rand(3,3)
a =
0.6212882 0.5211472 0.0881335
0.3454984 0.2870401 0.4498763
0.7064868 0.6502795 0.7227253
Access the first value:
-->a(1)
ans =
0.6212882
-->a(1,1)
ans =
0.6212882
Access the second value:
-->a(2)
ans =
0.3454984
-->a(2,1)
ans =
0.3454984
So that proves how the single indexing works. Now to apply it to your problem and knocking out a for-loop.
// Create some matrix A
A = zeros(8,8)
//initialize the array of indices
index = [];
// Get the dimensions of A
rows = size(A,1);
cols = size(A,2);
x = 0;
for i=1:length(A)
if(A(i)==x)
// Append it to list using $ (last index) + 1
index($+1) = i;
end
end
Without for-loop
If you just need the values that adhere to a certain condition you could also do something like this
values = A(A==x);
Be carefull when comparing doubles, these are not always (un)equal when you expect.

processing 2 dimension array

I am working in classic ASP; using getRows to get multidimension array of rows and column.
while iterating a row; I want to pass that single row into another function to build the column layout.
with C# I can do this:
obj[][] multiDimArray = FunctionCall_To_InitializeArray_4X16();
for (int rowId = 0 ; rowId < 4 ; rowId++)
{
FunctionCall_to_ProcessSingleRow(multiDimArray[rowId][]);
//this function only accept single dimension array
}
How can I do this is asp classic/vbscript:
1. I have a function that accept single dimension array as parameter.
2. Call that function and pass 1 part of 2 dimension array.
Thank you
I think you will need to populate a new array or dictionary object with the single dimension you want to process.
here a piece from working code, should get you going..
aResults = oRst.Getrows
oRst.Close
Set oRst = Nothing
Call SubCloseDatabaseOracle
iRows = UBound(aResults, 2)
iCols = UBound(aResults, 1)
row = 1 'first row
line = ""
separator = ""
FOR col = 0 TO iCols
line = line & separator & cStr(aResults(col,row))
separator = ";"
NEXT
aSingleDimensionArray = split(line,";")

Resources