2017-01-25 2 views
1

Я новичок в python и пытаюсь выяснить, как петлю над матрицей 2x2.Как петля над 2D-матрицей с условием

Моя начальная точка - это *. CSV-файл, содержащий огромное количество данных (10 столбцов с 173828 строками). Потому что мне нужна только первый столбец (значения sigma_0) и шестой столбец (дата), я сделал матрицу под названием sigma_JD, которая содержит только эти две колонки:

import csv 
    import numpy as np 
    with open("C:/Users/.../03971822.csv") as input_file: 
     reader = csv.reader(input_file) 

     array = [] 
     for row in reader: 
     array.append(row) 

    matrix = np.asmatrix(array) 
    idx_IN_columns = [0, 5] 
    sigma_JD = matrix[:, idx_IN_columns] 
    print(sigma_JD) 
    print("size sigma_JD: ", np.shape(sigma_JD)) 

    >>> print(sigma_JD) 
    [['-12.42' '2451544.576'] 
    ['-12.92' '2451544.576'] 
    ['-12.45' '2451544.576'] 
    ..., 
    ['-11.66' '2454688.389'] 
    ['-12.61' '2454688.389'] 
    ['-11.72' '2454688.389']] 
    >>> print("size sigma_JD: ", np.shape(sigma_JD)) 
    size sigma_JD: (173828, 2) 

Теперь я хочу, чтобы петли по второй колонке - Дата; это проявляется в определенном смысле, это называется «Julian Day», например, значения JD являются

  2451544,5 = 01/January/2000 0:00 
      2451545,5 = 02/January/2000 0:00 
      2451546,5 = 03/January/2000 0:00 

2451544 рассказывает день/месяц/год, десятичное место говорит время.

Я хочу написать код, в котором учитываются все значения sigma_0, которые находятся в течение одного дня. Таким образом, цикл должен работать с определенными значениями, а не посредством индексации.

Он должен начинаться с 2451544,5, а затем принимать во внимание все значения sigma_0, которые находятся в течение одного дня (и суммирует его), а затем перейти на следующий день 2451544,5 и сделать то же самое ... .

Я пробовал s.th. как это, но он не работает

x = 2451544.5 
    y = x + 1 
    for i in sigma_JD[:, 1]: 
     while x < y: 
    print(sigma_JD[i, 1]) 
    break 

Тогда я подумал о создании моей собственной функции, но не получилось, что далеко:

def select(x): 
    count = 2451544.5 
    select = [] 
    for i in range(0, len(x[:, 1])): # loop over Julian Day 
     if count < count + 1: 
     row = [] 
     for j in range(0, len(x[:, 0])): # loop over sigma_0 values 
      # take all sigma_0 values and sum it up 
     count += 1 
    return select 

Было бы очень, очень хорошо, если бы кто-то мог Помоги мне. Я работаю над этим целыми днями, и это действительно раздражает меня, что я не знаю, как это сделать.

Большое спасибо.

+1

Вы могли бы рассмотреть с помощью панда для эти задачи. Он использует numpy под капотом, но он позволяет вам читать csv, преобразовывать столбец datetime в даты и предоставляет простые в использовании функции groupby. http://pandas.pydata.org/pandas-docs/stable/index.html –

ответ

0

Дайте этот снимок (возможно, потребуется загрузить jdcal package)

import csv 
import collections 
from jdcal import jd2gcal 

with open("test.csv") as input_file: 
    reader = csv.reader(input_file) 

    jd_sigma_map = collections.defaultdict(int) 
    jd_sigma_count = collections.defaultdict(int) 

    for row in reader: 

     #convert to the normal date format 
     year, month, dd, ms = jd2gcal(float(row[5]), 0) 

     #use date as key 
     date_key = '%s-%s-%s' % (year, month, dd) 

     #Sum sigma values for same key (day) 
     jd_sigma_map[date_key] += float(row[0]) 
     jd_sigma_count[date_key] += 1 

Файл для тестирования (test.csv):

-12.42, 0, 0, 0, 0, 2451544.576 
-12.92, 0, 0, 0, 0, 2451544.576 
-5.92, 0, 0, 0, 0, 2451545.677 
-2.92, 0, 0, 0, 0, 2451545.699 
-16.61, 0, 0, 0, 0, 2454688.310 
-11.66, 0, 0, 0, 0, 2454688.389 
-12.61, 0, 0, 0, 0, 2454688.400 

Выход:

#For ordered (by date) output 
ordered_dict = collections.OrderedDict(sorted(jd_sigma_map.items())) 

for k, v in ordered_dict.items(): 
    average = float(v/jd_sigma_count[k]) 
    print("Sigma value for day %s = %0.3f \t(over %d days)\tAverage = %0.3f" 
      % (k, v, jd_sigma_count[k], average)) 

# Sigma value for day 2000-1-1 = -25.340 (over 2 days) Average = -12.670 
# Sigma value for day 2000-1-2 = -8.840 (over 2 days) Average = -4.420 
# Sigma value for day 2008-8-9 = -40.880 (over 3 days) Average = -13.627 

Примечания:

  • Использование словаря позволяет нам «удерживать» значение сигмы за каждый день. Делает это проще, чем возиться с массивом 2x2.
  • Выход, jd_sigma_map - это словарь с ключом, являющимся днем ​​в формате YYYY-MM-DD, а значение - общие значения сигмы для дня. Нам не нужен формат, мы просто хотим, чтобы каждый ключ за день был уникальным
  • Как вы можете сказать, я сделал весь анализ «на лету» во время чтения CSV, вы можете либо сохранить это в списке, и закрыть сообщение после закрытия файла.
  • Python 3 решения (изменение print() к print ... и items() в iteritems() для Python 2.x)
  • См this question сортировать выходной словарь (добавляемый в коде)
+0

Thx пока что код работает отлично. Я также сохранил вывод в новом файле. Есть ли способ увидеть, сколько значений sigma_0 в течение одного дня принимается во внимание? Потому что, actualIy мне нужно среднее значение sigma_0 для каждого дня (и не только сумма). – user7448207

+0

Не беспокойтесь, рад, что я мог бы помочь! Я обновил ответ в соответствии с запросом - это простое решение проблемы. К сожалению, я не смог придумать «более аккуратное» решение, которое воспользовалось бы существующими структурами данных (например, сменив словарь '_map', чтобы иметь значения кортежа' (значение, счет) ') –

+0

Еще раз спасибо за вашу помощь. Я возился с идеей сделать запрос до начала всего словаря. Например, у меня есть седьмой столбец с значениями расстояния (от 0 до 20 000), и я сначала позволю пользователю ответить на вопрос [«distance = input (« Тип Pls на расстоянии/радиус: »), и, соответственно, Значения sigma_0 будут суммироваться и усредняться. Возможно ли это? – user7448207

0
import numpy as np 

array = [['-12.42', '2451544.576'], 
    ['-12.92', '2451544.576'], 
    ['-12.45', '2451544.576'], 
    ['-11.66', '2454688.389'], 
    ['-12.61', '2454688.389'], 
    ['-11.72', '2454688.389']] 


matrix = np.asmatrix(array) 
print matrix 
for (i, j), ele in np.ndenumerate(matrix): 
    if j == 1: #SECOND COL 
     print i, j, ele 
Смежные вопросы