aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorPaulo Custodio <pauloscustodio@gmail.com>2023-04-02 01:02:43 +0100
committerPaulo Custodio <pauloscustodio@gmail.com>2023-04-02 01:02:43 +0100
commit53c8b0a71f6e456fcf6041b760987ba8e8274454 (patch)
tree5c59f2770d0b44b7b6ae3115f3c5f9cd048f8dbf
parent509b3203f4c28a63729d78c92bbae7b5bbc939da (diff)
downloadperlweeklychallenge-club-53c8b0a71f6e456fcf6041b760987ba8e8274454.tar.gz
perlweeklychallenge-club-53c8b0a71f6e456fcf6041b760987ba8e8274454.tar.bz2
perlweeklychallenge-club-53c8b0a71f6e456fcf6041b760987ba8e8274454.zip
Add C solution
-rw-r--r--challenge-181/paulo-custodio/c/ch-2.c120
1 files changed, 120 insertions, 0 deletions
diff --git a/challenge-181/paulo-custodio/c/ch-2.c b/challenge-181/paulo-custodio/c/ch-2.c
new file mode 100644
index 0000000000..9fec9f8be0
--- /dev/null
+++ b/challenge-181/paulo-custodio/c/ch-2.c
@@ -0,0 +1,120 @@
+/*
+Challenge 181
+
+Task 2: Hot Day
+Submitted by: Mohammad S Anwar
+
+You are given file with daily temperature record in random order.
+
+Write a script to find out days hotter than previous day.
+Example
+
+Input File: (temperature.txt)
+
+2022-08-01, 20
+2022-08-09, 10
+2022-08-03, 19
+2022-08-06, 24
+2022-08-05, 22
+2022-08-10, 28
+2022-08-07, 20
+2022-08-04, 18
+2022-08-08, 21
+2022-08-02, 25
+
+Output:
+2022-08-02
+2022-08-05
+2022-08-06
+2022-08-08
+2022-08-10
+*/
+
+#include <stdio.h>
+#include <stdlib.h>
+#include <string.h>
+#include <stdbool.h>
+
+struct data {
+ long jd; // julian day
+ int temp; // temperature
+};
+
+struct data* data = NULL;
+int data_size = 0;
+
+void* check_mem(void* p) {
+ if (!p) {
+ fputs("Out of memory", stderr);
+ exit(EXIT_FAILURE);
+ }
+ return p;
+}
+
+// https://pdc.ro.nu/jd-code.html
+long gregorian_date_to_jd(int y, int m, int d) {
+ y += 8000;
+ if (m < 3) { y--; m += 12; }
+ return (y * 365) + (y / 4) - (y / 100) + (y / 400) - 1200820
+ + (m * 153 + 3) / 5 - 92 + d - 1;
+}
+
+void jd_to_gregorian_date(long jd, int* yp, int* mp, int* dp) {
+ int y, m, d;
+ for (y = jd / 366 - 4715; gregorian_date_to_jd(y + 1, 1, 1) <= jd; y++);
+ for (m = 1; gregorian_date_to_jd(y, m + 1, 1) <= jd; m++);
+ for (d = 1; gregorian_date_to_jd(y, m, d + 1) <= jd; d++);
+ *yp = y; *mp = m; *dp = d;
+}
+
+void read_data(const char* filename) {
+ FILE* fp = fopen(filename, "r");
+ if (fp == NULL) {
+ perror(filename);
+ exit(EXIT_FAILURE);
+ }
+
+ char line[BUFSIZ];
+ while (fgets(line, sizeof(line), fp)) {
+ int y,m,d,t;
+ if (sscanf(line, "%d-%d-%d, %d", &y, &m, &d, &t) != 4) {
+ fprintf(stderr, "cannot parse: %s\n", line);
+ exit(EXIT_FAILURE);
+ }
+ struct data d1;
+ d1.jd = gregorian_date_to_jd(y, m, d);
+ d1.temp = t;
+
+ data_size++;
+ data = check_mem(realloc(data, data_size*sizeof(struct data)));
+ data[data_size-1] = d1;
+ }
+
+ fclose(fp);
+}
+
+int compare(const void* a, const void* b) {
+ return ((struct data*)a)->jd - ((struct data*)b)->jd;
+}
+
+void print_hot_days() {
+ qsort(data, data_size, sizeof(struct data), compare);
+ for (int i = 1; i < data_size; i++) {
+ if (data[i].temp > data[i-1].temp) {
+ int y, m, d;
+ jd_to_gregorian_date(data[i].jd, &y, &m, &d);
+ printf("%04d-%02d-%02d\n", y, m, d);
+ }
+ }
+}
+
+int main(int argc, char* argv[]) {
+ if (argc != 2) {
+ fputs("usage: ch-2 temperature-file\n", stderr);
+ return EXIT_FAILURE;
+ }
+
+ read_data(argv[1]);
+ print_hot_days();
+ free(data);
+}